In: Computer Science
UNIX/LINUX LAB
(1) Review the sample shell program (tryShell.c), and compile/run the program (tryShell) with the following commands,
and at the end, use CTRL+C to terminate the program:
ls
ls -l tryShell*
date
whoami
hostname
uname -a
ctrl+C
(2) Run the program (tryShell) with "time -p" with a few commands:
time -p ./tryShell
(3) Edit the program (tryShell.c) so that it will exit (terminate the program) when the input command string is "exit"
try shell.c code at bottom
////////////
#include
#include
#include
#include
#include
#define MAX 1024
void parse(char *line, char **argv)
{
while (*line != '\0') { /* if not the end of line */
while (*line == ' ' || *line == '\t' || *line == '\n')
*line++ = '\0'; /* replace white spaces with 0*/
*argv++ = line; /* save the argument position */
while (*line != '\0' && *line != ' ' &&
*line != '\t' && *line != '\n')
line++; /* skip the argument until ... */
}
*argv = '\0'; /* mark the end of argument list */
}
void execute(char **argv)
{
pid_t pid;
int status;
if ((pid = fork()) < 0) { /* fork a child process */
printf("*** ERROR: forking child process failed\n");
exit(1);
}
else if (pid == 0) { /* for the child process: */
if (execvp(*argv, argv) < 0) { /* exec command */
printf("*** ERROR: exec failed\n");
exit(1);
}
}
else { /* for the parent: */
while (wait(&status) != pid) /* wait for completion */
;
}
}
void main(void)
{
char line[MAX]; /* the input line */
char *argv[64]; /* the command line argument */
while (1) { /* repeat until done .... */
printf("Shell -> "); /* display a prompt */
if (fgets(line, MAX, stdin) != 0){
line[strcspn(line, "\n")] = '\0';
printf("\n");
// Place your code here to check the command is "exit"
// to terminate the shell.
parse(line, argv); /* parse the line */
execute(argv); /* otherwise, execute cmd */
}
}
}
///////////
1)
./tryShell
Shell -> ls
hello hello1 hello.c shell.o tryShell tryShell.c
tryShell.o
Shell -> ls -l tryShell*
ls: tryShell*: No such file or directory
Shell -> ls -l tryShell
-rwxr-xr-x+ 1 saes0817 ice 8470 Oct 10 10:44 tryShell
Shell -> date
Sat Oct 10 10:51:39 EDT 2020
Shell -> whoami
saes0817
Shell -> hostname
devapp714cn
Shell -> uname -a
Linux devapp714cn 2.6.18-308.el5 #1 SMP Fri Jan 27 17:17:51 EST
2012 x86_64 x86_64 x86_64 GNU/Linux
Shell ->
2)
time -p ./tryShell
Shell -> ls
hello hello1 hello.c shell.o tryShell tryShell.c
tryShell.o
Shell -> date
Sat Oct 10 10:55:11 EDT 2020
Shell -> hostname
devapp714cn
Shell ->
real 14.35
user 0.00
sys 0.01

3) tryShell.c file with exit code
#include <stdio.h>
#include <sys/types.h>
#include <unistd.h>
#include <sys/types.h>
#define MAX 1024
void parse(char *line, char **argv)
{
while (*line != '\0') { /* if not the end of line */
while (*line == ' ' || *line == '\t' || *line == '\n')
*line++ = '\0'; /* replace white spaces with 0*/
*argv++ = line; /* save the argument position */
while (*line != '\0' && *line != ' ' &&
*line != '\t' && *line != '\n')
line++; /* skip the argument until ... */
}
*argv = '\0'; /* mark the end of argument list */
}
void execute(char **argv)
{
pid_t pid;
int status;
if ((pid = fork()) < 0) { /* fork a child process */
printf("*** ERROR: forking child process failed\n");
exit(1);
}
else if (pid == 0) { /* for the child process: */
if (execvp(*argv, argv) < 0) { /* exec command */
printf("*** ERROR: exec failed\n");
exit(1);
}
}
else { /* for the parent: */
while (wait(&status) != pid) /* wait for completion */
;
}
}
void main(void)
{
char line[MAX]; /* the input line */
char *argv[64]; /* the command line argument */
while (1) { /* repeat until done .... */
printf("Shell -> "); /* display a prompt */
if (fgets(line, MAX, stdin) != 0){
line[strcspn(line, "\n")] = '\0';
printf("\n");
// Place your code here to check the command is "exit"
// to terminate the shell.
if (0 == strcmp(line, "exit")){
exit(1);
}
parse(line, argv); /* parse the line */
execute(argv); /* otherwise, execute cmd */
}
}
}
///////////
OUTPUT:
./tryShell
Shell -> ls
hello hello1 hello.c shell.o tryShell tryShell.c
tryShell.o
Shell -> exit
bash-3.2$
bash-3.2$
bash-3.2$