2009-10-03 12 views
2

c pour la capture du clavier. Le code suivant est détecté lorsqu'une touche fléchée/esc est enfoncée. En même temps je veux lire des mots entiers que les entrées d'utilisateur et ceux-ci devraient être montrés sur stdout aussi bien.En utilisant getchar() après read()

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. 

Mais ce code ne fonctionne pas si je supprime '\ n'. Je veux que stdout se comporte comme un shell normal.

Répondre

2

printf(3) passe par la fonction d'E/S tamponnée <stdio.h>, qui inclut fputs(3) et fputc(3). Vous observez le comportement de mise en mémoire tampon de ligne normale. Vous pouvez vaincre ce tampon comme noté avec setbuf(3), cependant, puisque vous ne le voulez pas en premier lieu et vous utilisez déjà un appel direct du noyau (read(2)) pour la lecture, pourquoi ne pas changer votre logique juste un peu pour appeler directement le noyau avec write(2) aussi bien?

char buffer[100]; 

int n; 

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

Et si vous vouliez, vous pouvez définir votre propre directPrintf pour vous faciliter la tâche:

#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() est probablement implémenté en termes de read() qui lit beaucoup plus de 1 octet (généralement un entier PIPE_BUF ou 4096 octets). Il maintient ensuite un curseur privé sur ce tampon, en extrayant des octets si nécessaire.

Ceci est fait parce que read() a un surdébit non-trivial associé avec juste appelant il.

printf(), et fwrite() (et etc) également tampon pour la même raison (write() a un surdébit non trivial). L'appel à fflush(stdout) se traduira par un appel write() de tout ce qui a été tamponné, mais pas envoyé au port d'E/S sous-jacent.

Enfin, vous avez \n\r en arrière; il est presque certainement censé être \r\n

0

insert

setbuf(stdout, NULL); 

quelque part au début et à enlever le \ n.