{"id":3675,"date":"2019-07-20T00:01:49","date_gmt":"2019-07-20T07:01:49","guid":{"rendered":"https:\/\/c-for-dummies.com\/blog\/?p=3675"},"modified":"2019-08-10T09:42:52","modified_gmt":"2019-08-10T16:42:52","slug":"un-buffering-output","status":"publish","type":"post","link":"https:\/\/c-for-dummies.com\/blog\/?p=3675","title":{"rendered":"Un-Buffering Output"},"content":{"rendered":"<p>Last year, I wrote about <a href=\"https:\/\/c-for-dummies.com\/blog\/?p=3021\">using the standard error device<\/a> <em>stderr<\/em> to generate output that can&#8217;t be redirected. This technique is often used to send error messages to the console, though I noted how these messages may show up out of sync with standard output. This situation can be resolved, providing you know how to flush the <em>stderr<\/em> device buffer.<br \/>\n<!--more--><br \/>\nWhat a wonderful word, <em>flush<\/em>. It&#8217;s appropriate, and the action taken is like flushing your favorite porcelain seat: Contents are immediately released.<\/p>\n<p>In C, you can flush any output stream. The effect is that any data waiting in the buffer is rushed out the door. This effect applies to open files as well as the <em>stdout<\/em> and <em>stderr<\/em> devices. The function is called <em>fflush()<\/em> and it&#8217;s defined in the <code>stdio.h<\/code> header file. Here&#8217;s the man page format:<\/p>\n<p><code>int fflush(FILE *stream);<\/code><\/p>\n<p><code>stream<\/code> is a <em>FILE<\/em> pointer, which by definition can include the standard output and standard error devices, constants <em>sdtout<\/em> and <em>stderr<\/em>. Therefore, you can use the <em>fflush()<\/em> function to immediately dump error message output:<\/p>\n<p><code>fprintf(stderr,\"Something went horribly awry!\\n\");<br \/>\nfflush(stderr);<\/code><\/p>\n<p>The effect of these two statements is to immediately output the message <code>Something went horribly awry!<\/code> to the console. This output doesn&#8217;t stop the program or alter any other behavior. The text is output regardless of any I\/O redirection or filters.<\/p>\n<p>Gander at the following code:<\/p>\n<pre class=\"screen\">\r\n#include &lt;stdio.h&gt;\r\n\r\nint main()\r\n{\r\n    const char normal[] = \"Normal output \";\r\n    const char error[] = \"Error output \";\r\n\r\n    fprintf(stdout,normal);\r\n    fprintf(stderr,error);\r\n    fprintf(stdout,normal);\r\n    fprintf(stderr,error);\r\n    fprintf(stdout,normal);\r\n    fprintf(stderr,error);\r\n\r\n    return(0);\r\n}<\/pre>\n<p>A series of <em>fprintf()<\/em> statements output the two strings, one sent to the <code>stdout<\/code> device and the other to <code>stderr<\/code>. You would think the output would alternate, but here&#8217;s what the program coughs up:<\/p>\n<p><code>Error output Error output Error output Normal output Normal output Normal output<\/code><\/p>\n<p>All the output to the <code>stderr<\/code> device appears first, followed by all the output to <code>stdout<\/code>. It&#8217;s unexpected, but demonstrates the buffered nature of the stream.<\/p>\n<p>I know two ways to fix the output. First, you can modify each string by appending a newline, <code>'\\n'<\/code>. This character helps flush the output buffer, making the output alternate as you would expect. The problem with this solution is that it may not work for larger programs with a long runtime. Regardless, to guarantee instant output, use the <em>fflush()<\/em> function:<\/p>\n<pre class=\"screen\">\r\n#include &lt;stdio.h&gt;\r\n\r\nint main()\r\n{\r\n    const char normal[] = \"Normal output \";\r\n    const char error[] = \"Error output \";\r\n\r\n    fprintf(stdout,normal);\r\n    fflush(stdout);\r\n    fprintf(stderr,error);\r\n    fflush(stderr);\r\n    fprintf(stdout,normal);\r\n    fflush(stdout);\r\n    fprintf(stderr,error);\r\n    fflush(stderr);\r\n    fprintf(stdout,normal);\r\n    fflush(stdout);\r\n    fprintf(stderr,error);\r\n    fflush(stderr);\r\n\r\n    return(0);\r\n}<\/pre>\n<p>After each <em>fprintf()<\/em> statement, the buffer is flushed. With this modification, the output appears as expected, forced that way thanks to <em>fflush()<\/em>:<\/p>\n<p><code>Normal output Error output Normal output Error output Normal output Error output<\/code><\/p>\n<p>Some notes:<\/p>\n<p>Using the <em>fflush()<\/em> function doesn&#8217;t close the output stream. The <code>stdout<\/code> and <code>stderr<\/code> streams are always open. For files, however, be aware that using <em>fflush()<\/em> won&#8217;t close the file; it must still be closed properly when you&#8217;re done writing data.<\/p>\n<p>The <em>fflush()<\/em> function&#8217;s <em>stream<\/em> argument can be replace with <code>NULL<\/code> to flush all open output streams.<\/p>\n<p>Also see <a href=\"https:\/\/c-for-dummies.com\/blog\/?p=3701\">this blog post<\/a> on the <em>setbuf()<\/em> function.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>It&#8217;s possible to output messages to the stream immediately, providing you know how to flush. <a href=\"https:\/\/c-for-dummies.com\/blog\/?p=3675\">Continue reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[2],"tags":[],"class_list":["post-3675","post","type-post","status-publish","format-standard","hentry","category-main"],"_links":{"self":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts\/3675","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=3675"}],"version-history":[{"count":6,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts\/3675\/revisions"}],"predecessor-version":[{"id":3714,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=\/wp\/v2\/posts\/3675\/revisions\/3714"}],"wp:attachment":[{"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=3675"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=3675"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/c-for-dummies.com\/blog\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=3675"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}