2009-10-03 3 views
2

c для захвата клавиатуры. После ввода кода при нажатии клавиши со стрелкой/esc. В то же время я хочу прочитать целые слова, что пользовательские входы, и они должны быть показаны на stdout.Использование getchar() после чтения()

char pp = 0; 
char p = 0; 
while((i = read(0, &c, 1)) == 1) { 
if (pp == 033 && p == 0133 && (c &= 255) == 0102) /* DOWN */ break; 
if (c == 0177) /* ASCII DELETE */ break; 
printf("%o, %o, %o\t%s\n\r", pp, p, c, &c); 
pp = p; 
p = c; 
} 
... 
... 
getchar(); //I want to capture here what was entered before 
      // **return key** was pressed. 

Но этот код не работает, если я удаляю '\ n'. Я хочу, чтобы stdout должен вести себя как обычная оболочка.

ответ

2

printf(3) проходит через буферную установку ввода-вывода <stdio.h>, которая включает в себя fputs(3) и fputc(3). Вы наблюдаете обычное поведение буферизации линии. Вы можете победить эту буферизацию, как указано в setbuf(3), однако, поскольку вы не хотите ее в первую очередь, и вы уже используете прямой вызов ядра (read(2)) для чтения, почему бы не немного изменить свою логику, чтобы напрямую вызвать Ядро с write(2)?

char buffer[100]; 

int n; 

n = snprintf(buffer, sizeof buffer, "format string...", args...); 
write(1, buffer, n) 

И если вы хотите, вы можете определить свой собственный directPrintf, чтобы сделать это проще:

#include <stdio.h> 
#include <stdarg.h> 
#include <unistd.h> 

int directPrintf(const char *format, ...) 
{ 
va_list ap; 
char buffer[200]; 

    va_start(ap, format); 
    int n = vsnprintf(buffer, sizeof buffer, format, ap); 
    va_end(ap); 
    return write(1, buffer, n); 
} 
0

getchar(), скорее всего, реализован в терминах read(), который читает гораздо больше 1 байт (обычно PIPE_BUF, или 4096 байт). Затем он поддерживает частный курсор в этот буфер, извлекая байты по мере необходимости.

Это сделано, потому что read() имеет нетривиальные служебные данные, связанные только с , вызывающие.

printf() и fwrite() (и т. Д.) Также буфер по той же причине (write() имеет нетривиальные накладные расходы). Вызов fflush(stdout) приведет к вызову write() того, что было буферизировано, но не отправлено на базовый порт ввода-вывода.

И, наконец, у вас есть \n\r назад; это почти наверняка должно быть \r\n

Смежные вопросы