Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>You're doing IO incorrectly, the POSIX manual and all other related documentation explicitly says never to mix IO done on <code>FILE *</code>s and file descriptors. You have very blatantly broken this rule. This rule is in place because <code>FILE *</code>s use <strong>buffering</strong> an this means that after a call to <a href="http://linux.die.net/man/3/fgets" rel="nofollow noreferrer"><code>fgets</code></a> there will be nothing left for <code>read</code> to get because <code>fgets</code> already read all pending data into a buffer that is kept in the <code>FILE *</code> structure.</p> <p>So since there's no way to check if an ISO C IO method will block, we have to use file descriptors only.</p> <p>Since we know that <code>STDIN_FILENO</code> is just the number 0, we can use </p> <pre><code>fcntl (0, F_SETFL, O_NONBLOCK); </code></pre> <p>this will turn all <a href="http://linux.die.net/man/2/read" rel="nofollow noreferrer"><code>read</code></a>s on file descriptor 0 to non-blocking mode, if you want to use a different file descriptor so that you can leave 0 alone then just use <a href="http://linux.die.net/man/2/dup" rel="nofollow noreferrer"><code>dup</code></a> to duplicate it.</p> <p>This way, you can stay away from <a href="http://linux.die.net/man/2/poll" rel="nofollow noreferrer"><code>poll</code></a> completely and implement <code>ngetc</code> as</p> <pre><code>ssize_t ngetc (char *c) { return read (0, c, 1); } </code></pre> <p>or better yet, a macro</p> <pre><code>#define ngetc(c) (read (0, (c), 1)) </code></pre> <p>Thus you get a simple implementation for what you're looking for.</p> <p><strong>Edit:</strong> If you are still worried about the terminal buffering the input, you can always change the terminal's settings, see <a href="https://stackoverflow.com/questions/4506704/how-to-disable-line-buffering-of-input-in-xterm-from-program">How to disable line buffering of input in xterm from program?</a> for more information on how to do this.</p> <p><strong>Edit:</strong> The reason that one could not use <code>fgetc</code> instead of <code>read</code> is for the same reason that using <code>fgets</code> won't work. When one of the <code>FILE *</code> IO functions is run, it reads all the data from the associated file descriptor. But once that happens, <code>poll</code> will never return because it's waiting on a file descriptor that's always empty, and the same thing will happen with <code>read</code>. Thus, I suggest that you follow the advice of the documentation and <strong>never</strong> mix <em>streams</em> (IO using <code>fgets</code>, <code>fgetc</code>, etc.) and <em>file descriptors</em> (IO using <code>read</code>, <code>write</code>, etc.)</p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload