2

I'm working on a project where I call a function which triggers a segfault. I fixed this, but during the process I noticed the following.

When my code is of the format;

main(){
  ...
  std::cout << "Looking for segfault\n"; // this does not print
  buggyFunction(); // crashes in here
  ...
}

buggyFunction(){
  ...
  thing_that_causes_segfault;
  ...
}

The line "Looking for segfault" doesn't print to STD, and the program crashes in buggyFunction. Fine, but when I add a cout line inside buggyFunction();

main(){
  ...
  std::cout << "Looking for segfault\n"; // this now *does* print
  buggyFunction(); 
  ...
}

buggyFunction(){
  ...
  std::cout << "Now we're INSIDE buggy function\n"; // this prints too
  thing_that_causes_segfault;
  ...
}

Inside buggy function, both lines print (and then it crashes).

Why do we see this difference in ouput, depending on the addition of this extra output call? Is it related to the handling of streams, or something else? I'm using g++ (Ubuntu 4.4.3-4ubuntu5) 4.4.3.

Alex
  • 2,000
  • 4
  • 23
  • 41

3 Answers3

7

The reason for this is that cout has a buffer and it will only pass to the system function and write to the console when the buffer is full. Your second use of cout happens to overflow the buffer and so it calls the operating system and empties the buffer. If you want to guarantee that the output has left the buffer, you must use std::flush. You can both end a line and flush the buffer with std::endl.

Puppy
  • 144,682
  • 38
  • 256
  • 465
  • 2
    Alternatively, you can use `std::cerr`, which is unbuffered (presumably for the purpose of error reporting). – Kerrek SB Jul 27 '11 at 11:45
  • 1
    Even with `std::endl` instead of "\n" there is still no guarantee that the line will be printed, but the odds of the line being printed are much better with `std::endl`. Two reasons why this still might not work: (1) There might well be other buffering going on, and (2) SEGFAULT is a response to some kind of undefined behavior. There are no guarantees when it comes to undefined behavior. – David Hammen Jul 27 '11 at 11:48
  • D'OH!! I previously had an endl (specifically to flush the stream) but it got removed at some point in my debugging, and I forgot to put it back in - I rarely use \n for that very reason. – Alex Jul 27 '11 at 11:56
3

Because your line might not immediately printed out because it's cached and the cache is not "flushed". std::endl is an newline + a flush thus forces immediate printout:

std::cout << "Looking for segfault" << std::endl;
orlp
  • 112,504
  • 36
  • 218
  • 315
2

It has to do with buffering. Things that you write to cout are appended to an internal buffer that only gets flushed periodically. You can explicitly flush the buffer by writing std::flush to your stream, or replacing the "\n" with << std::endl.

NPE
  • 486,780
  • 108
  • 951
  • 1,012