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 ininit_cnt
, then constructs and initializes the objectscin
,cout
,cerr
,clog
wcin
,wcout
,wcerr
, andwclog
"
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
fromInit
.
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.293If a translation unit includesThe results of including<iostream>
or explicitly constructs anios_base::Init
object, these stream objects shall be constructed before dynamic initialization of non-local objects defined later in that translation unit.<iostream>
in a translation unit shall be as if<iostream>
defined an instance ofios_base::Init
with static lifetime. Similarly, the entire program shall behave as if there were at least one instance ofios_base::Init
with static lifetime.
Change [ios::Init]/3:
Init();-3- Effects: Constructs an object of class
Init
.IfConstructs and initializes the objectsinit_cnt
is zero, the function stores the value one ininit_cnt
, then constructs and initializes the objectscin
,cout
,cerr
,clog
(27.4.1),wcin
,wcout
,wcerr
, andwclog
(27.4.2). In any case, the function then adds one to the value stored ininit_cnt
.cin
,cout
,cerr
,clog
,wcin
,wcout
,wcerr
andwclog
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 inIf there are no other instances of the class still in existance, callsinit_cnt
and, if the resulting stored value is one,cout.flush()
,cerr.flush()
,clog.flush()
,wcout.flush()
,wcerr.flush()
,wclog.flush()
.