0

I am writing my own simple shell and currently I'm thinking of getting input ( command ) from user.

I wrote a following prototype:

 while(1) {
        printf("gsh> ");
        fflush(stdout);
        total_len = 0;
        do {
            len = read(0, buffer,  MAX_LENGTH_OF_COMMAND-total_len -1);
            total_len+= len;
            } while( buffer[total_len-1] != '\n');
        buffer[total_len]='\0';
        parse(buffer);
    }

And this soultion seems me to be best, but I am not sure. So, I am asking for correct and recommend/advice me something.

Thanks in advance.

3
  • read and fread are for reading fixed-size data. This is usually binary data which is organised in fixed-size blocks. You want to read lines of variable length. fgets is the function that does this for you. Or, if you want to write an interactive shell, you might consider unsing getline, which can be coupled with acommand history and which allows advanced line editing. Commented Sep 19, 2015 at 11:07
  • Consider using readline ( cnswww.cns.cwru.edu/php/chet/readline/rltop.html ). Commented Sep 19, 2015 at 11:21
  • What happens when read returns 0 or a negative value? Commented Sep 19, 2015 at 11:49

2 Answers 2

1

You may rather use getchar() so you can be able to catch keys like up and down arrow (usually useful for shell history) that generate more than one character when you press it. You may also want to make your terminal as raw to get non blocking inputs.

#include <termios.h>
#include <unistd.h>
int main()
{
  struct termios oldt;
  struct termios newt;

  tcgetattr(0, &oldt);
  memcpy(&newt, &oldt, sizeof(newt));
  cfmakeraw(&newt);
  tcsetattr(0, TCSANOW, &newt);
  /* your read function ...*/

  /* before exiting restore your term */                                                                   
  tcsetattr(0, TCSANOW, &oldt);
}
Sign up to request clarification or add additional context in comments.

Comments

0

A good way to create a custom prompt is using read. There is multiple ways so there is always a cleaner / better solution. But here is mine:

while ((fd = read(0, buff, BUFF_SIZE) > 0) {
    if (fd == BUFF_SIZE)
        // Command to big, handle this as you want to
    buff[fd - 1] = '\0';
    // Do what you want with your buff
}

Of course this solution has a max buffer size. You would need to wrap the read inside anoter function and use malloc to allocate the good size.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.