This page is a snapshot from the LWG issues list, see the Library Active Issues List for more information and the meaning of C++11 status.

### 1123. No requirement that standard streams be flushed

Section: 31.5.2.2.6 [ios.init] Status: C++11 Submitter: James Kanze Opened: 2009-05-14 Last modified: 2021-06-06

Priority: Not Prioritized

View all other issues in [ios.init].

View all issues with C++11 status.

Discussion:

As currently formulated, the standard doesn't require that there is ever a flush of `cout`, etc. (This implies, for example, that the classical hello, world program may have no output.) In the current draft (N2798), there is a requirement that the objects be constructed before `main`, and before the dynamic initialization of any non-local objects defined after the inclusion of `<iostream>` in the same translation unit. The only requirement that I can find concerning flushing, however, is in [ios::Init], where the destructor of the last `std::ios_base::Init` object flushes. But there is, as far as I can see, no guarantee that such an object ever exists.

Also, the wording in [iostreams.objects] says that:

> The objects are constructed and the associations are established at some time prior to or during the first time an object of class `ios_base::Init` is constructed, and in any case before the body of main begins execution.

In [ios::Init], however, as an effect of the constructor, it says that

> If `init_cnt` is zero, the function stores the value one in `init_cnt`, then constructs and initializes the objects `cin`, `cout`, `cerr`, `clog` `wcin`, `wcout`, `wcerr`, and `wclog`"

which seems to forbid earlier construction.

(Note that with these changes, the exposition only "`static int init_cnt`" in `ios_base::Init` can be dropped.)

Of course, a determined programmer can still inhibit the flush with things like:

>     new std::ios_base::Init ;       //  never deleted

or (in a function):

>     std::ios_base::Init ensureConstruction ;
>     //  ...
>     exit( EXIT_SUCCESS ) ;

Perhaps some words somewhere to the effect that all `std::ios_base::Init` objects should have static lifetime would be in order.

[ 2009 Santa Cruz: ]

> Moved to Ready. Some editorial changes are expected (in addition to the proposed wording) to remove `init_cnt` from `Init`.

Proposed resolution:

Change 31.4 [iostream.objects]/2:

> -2- The objects are constructed and the associations are established at some time prior to or during the first time an object of class `ios_base::Init` is constructed, and in any case before the body of main begins execution.292 The objects are not destroyed during program execution.293 If a translation unit includes `<iostream>` or explicitly constructs an `ios_base::Init` object, these stream objects shall be constructed before dynamic initialization of non-local objects defined later in that translation unit. The results of including `<iostream>` in a translation unit shall be as if `<iostream>` defined an instance of `ios_base::Init` with static lifetime. Similarly, the entire program shall behave as if there were at least one instance of `ios_base::Init` with static lifetime.

Change [ios::Init]/3:

>     Init();

> > -3- Effects: Constructs an object of class `Init`. If `init_cnt` is zero, the function stores the value one in `init_cnt`, then constructs and initializes the objects `cin`, `cout`, `cerr`, `clog` (27.4.1), `wcin`, `wcout`, `wcerr`, and `wclog` (27.4.2). In any case, the function then adds one to the value stored in `init_cnt`. Constructs and initializes the objects `cin`, `cout`, `cerr`, `clog`, `wcin`, `wcout`, `wcerr` and `wclog` if they have not already been constructed and initialized.

Change [ios::Init]/4:

>     ~Init();

> > -4- Effects: Destroys an object of class `Init`. The function subtracts one from the value stored in `init_cnt` and, if the resulting stored value is one, If there are no other instances of the class still in existance, calls `cout.flush()`, `cerr.flush()`, `clog.flush()`, `wcout.flush()`, `wcerr.flush()`, `wclog.flush()`.