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

165. xsputn(), pubsync() never called by basic_ostream members?

Section: 31.7.6.2 [ostream] Status: CD1 Submitter: Dietmar Kühl Opened: 1999-07-20 Last modified: 2016-01-28

Priority: Not Prioritized

View all other issues in [ostream].

View all issues with CD1 status.

Discussion:

Paragraph 2 explicitly states that none of the basic_ostream functions falling into one of the groups "formatted output functions" and "unformatted output functions" calls any stream buffer function which might call a virtual function other than overflow(). Basically this is fine but this implies that sputn() (this function would call the virtual function xsputn()) is never called by any of the standard output functions. Is this really intended? At minimum it would be convenient to call xsputn() for strings... Also, the statement that overflow() is the only virtual member of basic_streambuf called is in conflict with the definition of flush() which calls rdbuf()->pubsync() and thereby the virtual function sync() (flush() is listed under "unformatted output functions").

In addition, I guess that the sentence starting with "They may use other public members of basic_ostream ..." probably was intended to start with "They may use other public members of basic_streamuf..." although the problem with the virtual members exists in both cases.

I see two obvious resolutions:

  1. state in a footnote that this means that xsputn() will never be called by any ostream member and that this is intended.
  2. relax the restriction and allow calling overflow() and xsputn(). Of course, the problem with flush() has to be resolved in some way.

Proposed resolution:

Change the last sentence of 27.6.2.1 (lib.ostream) paragraph 2 from:

They may use other public members of basic_ostream except that they do not invoke any virtual members of rdbuf() except overflow().

to:

They may use other public members of basic_ostream except that they shall not invoke any virtual members of rdbuf() except overflow(), xsputn(), and sync().

[Kona: the LWG believes this is a problem. Wish to ask Jerry or PJP why the standard is written this way.]

[Post-Tokyo: Dietmar supplied wording at the request of the LWG. He comments: The rules can be made a little bit more specific if necessary be explicitly spelling out what virtuals are allowed to be called from what functions and eg to state specifically that flush() is allowed to call sync() while other functions are not.]