I’ve created a program that acts like a unix-shell. Namely if type something like “./helloWorld” it will execute the program and then wait for additional input. If the input is EOF (Ctrl + D) then the program must terminate.
What I’m struggling with is trying to compare the input without using getchar() or any method that requires additional input.
Here’s my code:
#include <stdio.h> #include <stdlib.h> #include <string.h> #include<unistd.h> /* for fork() */ #include<sys/types.h> /* for pid_t */ #include<sys/wait.h> /* fpr wait() */ int main(int argc, char* argv[]) { pid_t pid,waitPid; int status; char fileName[256]; while(!feof(stdin)) { printf(" %s > ", argv[0]); if (fgets(fileName, sizeof(fileName), stdin) != 0) { fileName[strcspn(fileName, "n")] = ''; //strcspn = calculates the length of the initial fileName segment, which consists of chars not in str2("n") char *args[129]; char **argv = args; char *cmd = fileName; const char *whisp = " tfrbn"; char *token; while ((token = strtok(cmd,whisp)) != 0) // strtok = breaks string into a series of tokens using the delimeter delim(whisp) { *argv++ = token; cmd = 0; }// /while if (getchar() == EOF) { break; } *argv = 0; pid = fork(); if (pid == 0){ execv(args[0], args); fprintf(stderr, "Oops! n"); } // /if waitPid = wait(&status); }// /if(fgets..) } // /while return 1;
}
I want to replace the
if (getchar() == EOF) { break; }
with a direct comparison. Like so: if (fileName == EOF) { break; }
Is this even possible? I’ve tried casting and other methods,but nothing has worked so far. Is there a different method that I haven’t thought of? To be more clear, I want to know if my thought is doable and if it is how to implement it. If not how can I terminate my program with CTRL + D and without additional input.
Advertisement
Answer
There is no way of comparing a string with EOF; it is not a char
value, but a condition on the stream (here, stdin
). However the getchar()
and alike will return the read char
value as unsigned char
cast to an int
, or EOF
if end-of-file was reached, or an error occurred.
The man page for fgets
says:
fgets(s, size, stream)
returnss
on success, andNULL
on error or when end of file occurs while no characters have been read.
After you get NULL
from fgets
you can use feof(stdin)
to test whether or not you’ve reached the end-of-file; or if it was because of an error; likewise you should be able to check the return value feof(stdin)
after reading each line with fgets
. If feof(stdin)
returns 0, then the end-of-file was not yet reached; if the return value is non-zero, it means that the EOF was reached.