Opened 8 years ago

Closed 7 years ago

#3323 closed Bugs (fixed)

file_descriptor_sink sink("abc", BOOST_IOS::trunc) not trunc

Reported by: qiaozhiqiang@… Owned by: turkanis
Milestone: Boost 1.40.0 Component: iostreams
Version: Boost 1.39.0 Severity: Problem
Keywords: file_descriptor_sink not trunc Cc:


boost 1.39.0 iostreams, on Windows Vista sp2: file_descriptor_sink sink("abc", BOOST_IOS::trunc) not trunc,

and file_descriptor_sink sink("abc", BOOST_IOS::app) only need call SetFilePointer?(pimpl_->handle_, 0, NULL, FILE_END) once, but now every write() call it once, why? if write only, can we call SetFilePointer?() in open() only once, and not set the flag impl::append?

void file_descriptor::open

( const std::string& path, BOOST_IOS::openmode m,

BOOST_IOS::openmode base )


using namespace std; m |= base;

#ifdef BOOST_IOSTREAMS_WINDOWS ---------------------------------------------

DWORD dwDesiredAccess; DWORD dwCreationDisposition; if ( (m & (BOOST_IOS::in | BOOST_IOS::out))


(BOOST_IOS::in | BOOST_IOS::out) )


if (m & BOOST_IOS::app)

throw BOOST_IOSTREAMS_FAILURE("bad open mode");

dwDesiredAccess = GENERIC_READ | GENERIC_WRITE; dwCreationDisposition =

(m & BOOST_IOS::trunc) ?


} else if (m & BOOST_IOS::in) {

if (m & (BOOST_IOS::app |BOOST_IOS::trunc))

throw BOOST_IOSTREAMS_FAILURE("bad open mode");

dwDesiredAccess = GENERIC_READ; dwCreationDisposition = OPEN_EXISTING;

} else if (m & BOOST_IOS::out) {

dwDesiredAccess = GENERIC_WRITE; dwCreationDisposition = OPEN_ALWAYS; if (m & BOOST_IOS::app)

pimpl_->flags_ |= impl::append;

} else {

throw BOOST_IOSTREAMS_FAILURE("bad open mode");


HANDLE handle =

::CreateFileA( path.c_str(),

dwDesiredAccess, FILE_SHARE_READ | FILE_SHARE_WRITE, NULL, lpSecurityAttributes dwCreationDisposition, FILE_ATTRIBUTE_NORMAL, NULL ); hTemplateFile

if (handle != INVALID_HANDLE_VALUE) {

pimpl_->handle_ = handle; pimpl_->flags_ |= impl::close_on_exit;

} else {

pimpl_->flags_ = 0; throw BOOST_IOSTREAMS_FAILURE("bad open");



std::streamsize file_descriptor::write(const char_type* s, std::streamsize n) { #ifdef BOOST_IOSTREAMS_WINDOWS

if (pimpl_->flags_ & impl::append) {

DWORD const dwResult =

::SetFilePointer?(pimpl_->handle_, 0, NULL, FILE_END);

if ( dwResult == INVALID_SET_FILE_POINTER &&

::GetLastError?() != NO_ERROR )


throw detail::bad_seek();


} DWORD ignore; if (!::WriteFile?(pimpl_->handle_, s, n, &ignore, NULL))

throw detail::bad_write();

return n;


Attachments (0)

Change History (2)

comment:1 Changed 7 years ago by steven_watanabe

(In [62934]) Rejigger file_descriptors handling of std::ios_base::openmode to match std::fstream. In particular, truncate existing files, if std::ios_base::trunc is passed. Refs #3323.

comment:2 Changed 7 years ago by steven_watanabe

  • Resolution set to fixed
  • Status changed from new to closed

(In [62935]) Open files in append mode on Windows instead of seeking to the end at every write when std::ios_base::app is passed. Fixes #3323.

Add Comment

Modify Ticket

Change Properties
Set your email in Preferences
as closed The owner will remain turkanis.
The resolution will be deleted. Next status will be 'reopened'.

E-mail address and user name can be saved in the Preferences.

Note: See TracTickets for help on using tickets.