-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmyshell.c
More file actions
142 lines (124 loc) · 3.38 KB
/
myshell.c
File metadata and controls
142 lines (124 loc) · 3.38 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
/* CS 347 -- Mini Shell!
* Original author Phil Nelson 2000
*/
#include <assert.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <errno.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <ctype.h>
#include "argparse.h"
#include "builtin.h"
#define MAX_USER_INPUT 1028 // define maximum user can input
/* PROTOTYPES */
void processline (char *line);
ssize_t getinput(char** line, size_t* size);
// helper functions
void freeargs(char** args, int count);
/* main
* This function is the main entry point to the program. This is essentially
* the primary read-eval-print loop of the command interpreter.
*/
int main () {
/*
* Start main shell
*/
char* line;
size_t size = 0;
while(1) {
getinput(&line, &size);
processline(line);
}
//write your code
//use getinput and processline as appropriate
return EXIT_SUCCESS;
}
/* getinput
* line A pointer to a char* that points at a buffer of size *size or NULL.
* size The size of the buffer *line or 0 if *line is NULL.
* returns The length of the string stored in *line.
*
* This function prompts the user for input, e.g., %myshell%. If the input fits in the buffer
* pointed to by *line, the input is placed in *line. However, if there is not
* enough room in *line, *line is freed and a new buffer of adequate space is
* allocated. The number of bytes allocated is stored in *size.
* Hint: There is a standard i/o function that can make getinput easier than it sounds.
*/
ssize_t getinput(char** line, size_t* size) {
ssize_t len = 1;
//write your code
if(*size == 0) { // if NULL allocate
*line = malloc(5);
*size = 5;
} else { // Empty
strcpy(*line, "");
}
printf("%%myshell%% ");
char input;
char* buff = malloc(MAX_USER_INPUT);
char* point = buff;
fgets(buff,MAX_USER_INPUT, stdin);
if(strlen(buff) == 0) {
perror("please enter an argument");
return 0;
}
while (*buff != '\0') {
len++;
if (len >= *size) {
*size += 1;
if(realloc(*line, *size) == NULL) {
perror("realloc error");
exit(-1);
}
}
strncat(*line, buff, 1);
buff++;
}
free(point);
return len;
}
/* processline
* The parameter line is interpreted as a command name. This function creates a
* new process that executes that command.
* Note the three cases of the switch: fork failed, fork succeeded and this is
* the child, fork succeeded and this is the parent (see fork(2)).
* processline only forks when the line is not empty, and the line is not trying to run a built in command
*/
void processline (char *line)
{
/*check whether line is empty*/
//write your code
pid_t cpid;
int status;
int argCount;
char** arguments = argparse(line, &argCount);
if (argCount == 0) {
return;
}
/*check whether arguments are builtin commands
*if not builtin, fork to execute the command.
*/
//write your code
if (!builtIn(arguments, argCount)) {
// if not a builtin function
// fork and call the appropriate unix command
if ((status = fork()) == 0) {
if (execvp(arguments[0], arguments)) {
perror("could not execute\n");
}
exit(1);
}
wait(NULL);
}
freeargs(arguments, argCount);
}
// helper function to free args malloc
void freeargs(char** args, int count) {
for (int i = 0; i < count; i++) {
free(args[i]);
}
free(args);
}