поэтому мы пишем оболочку Unix, способную запускать 11 команд, включая общеизвестные команды «который» и «где». Странно то, что две команды прекрасно работают примерно в 80% времени, а в остальное время они ничего не возвращают в пользовательском интерфейсе.
Понятно, когда я говорю 80% времени:Я имею в виду, что когда программа запущена и где / где работает, она продолжит работать до тех пор, пока программа не будет завершена и не будет перезапущена для следующей попытки. Если программа запускается и не работает, она продолжит не работать до тех пор, пока она не будет закрыта и перезапущена для следующей попытки.
Кроме того (ниже я расскажу об этом подробнее),ошибки сегмента оболочки, когда вы нажимаете клавишу ВВОД без команды, хотя она будет правильно реагировать при вводе бессмысленной команды.
Я пробовал много переборов для исправлений. Трудно понять, почему качество функциональности выглядит на первый взгляд случайным.
Возможно, Valgrind пролил некоторый свет на проблему, которую я опишу после вставки кода ниже.
//inits outside of while loop below
char *prompt = calloc(PROMPTMAX, sizeof(char));
char *commandline = calloc(MAX_CANON, sizeof(char));
char *command, *arg, *commandpath, *p, *pwd, *owd;
char **args = calloc(MAXARGS, sizeof(char*));
int uid, i, status, argsct, go = 1;
struct passwd *password_entry;
char *homedir;
char BUFFER[BUFFER_SIZE];
char PROMPT[BUFFER_SIZE];
struct pathelement *pathlist;
//inits inside of while loop below
int wc = 0;
char *input;
/* print your prompt */
printf("%s[%s]>", prompt_prefix, cwd);
/* get command line and process */
fgets(BUFFER, BUFFER_SIZE, stdin);
char delim[] = " \n\r";
input = strtok(BUFFER, delim);
char *cmdArray[BUFFER_SIZE];
while(input != NULL){
cmdArray[wc] = input;
input = strtok(NULL, " \n\r");
wc++;
}
//where function below
char *where(char *command, struct pathelement *pathlist ){
char BUFFER[BUFFER_SIZE];
struct pathelement *current = pathlist;
DIR *dr;
struct dirent *de;
strcpy(BUFFER, "");
while(current != NULL){
char *path = current->element;
dr = opendir(path);
if(dr){
while((de = readdir(dr)) != NULL){
if(strcmp(de->d_name, command) == 0){
strcat(BUFFER, path);
strcat(BUFFER, "/");
strcat(BUFFER, de->d_name);
strcat(BUFFER, "\n");
}
}
}
closedir(dr);
current = current->next;
}
int len = (int) strlen(BUFFER);
char *p = (char *) malloc(len);
BUFFER[len - 1] = '\0';
strcpy(p, BUFFER);
return p;
}
//if statement that implements where function
else if(strcmp(cmdArray[0], commands[2]) == 0){//where command
if(cmdArray[1] == NULL){
printf("Failed to run\n");
}
else{
for(int loopCount2 = 1; i < MAXARGS; loopCount2++){
if(cmdArray[loopCount2] != NULL){
char *result = where(cmdArray[loopCount2], pathlist);//loopCount2?
if(result != NULL){
printf("%s\n", result);
free(result);
}
else{
printf("%s not found\n", cmdArray[loopCount2]);
}
}
else{
break;
}
}
}
}
Вероятно, важно отметить, что хотя функции работают большую часть времени, "valgrind --track-originins = yes ./mysh" поднимает следующую проблему в 100% случаев:
"Условный переход или перемещение зависитдля неинициализированных значений (s) в (некоторое шестнадцатеричное значение) sh (sh.c: 155) по (некоторое шестнадцатеричное значение) main (main.c: 12) Неинициализированное значение было создано при выделении стека в (некоторое шестнадцатеричное значение) sh (sh.c: 25) "
Странно то, что когда я смотрю на строки, на которые указывает valgrind, они кажутся действительно инициализированными значениями (по моему очень любительскому мнению кодирования)
PS Я вижу, что последняя часть кода, которую я пытаюсь опубликовать, плохо отформатирована в предварительном просмотре, я попытаюсь отредактировать ее, чтобы ее было легко читать в ближайшее время