diff --git a/include/asio/detail/impl/win_iocp_file_service.ipp b/include/asio/detail/impl/win_iocp_file_service.ipp index a1a75036..3432b1e7 100644 --- a/include/asio/detail/impl/win_iocp_file_service.ipp +++ b/include/asio/detail/impl/win_iocp_file_service.ipp @@ -67,6 +67,8 @@ asio::error_code win_iocp_file_service::open( access = GENERIC_WRITE; else if ((open_flags & file_base::read_write) != 0) access = GENERIC_READ | GENERIC_WRITE; + else if ((open_flags & file_base::append) != 0) + access = GENERIC_WRITE; DWORD share = FILE_SHARE_READ | FILE_SHARE_WRITE; @@ -82,6 +84,8 @@ asio::error_code win_iocp_file_service::open( { if ((open_flags & file_base::truncate) != 0) disposition = TRUNCATE_EXISTING; + else if ((open_flags & file_base::append) != 0) + disposition = OPEN_ALWAYS; else disposition = OPEN_EXISTING; } @@ -94,6 +98,7 @@ asio::error_code win_iocp_file_service::open( if ((open_flags & file_base::sync_all_on_write) != 0) flags |= FILE_FLAG_WRITE_THROUGH; + impl.offset_ = 0; HANDLE handle = ::CreateFileA(path, access, share, 0, disposition, flags, 0); if (handle != INVALID_HANDLE_VALUE) { @@ -109,10 +114,24 @@ asio::error_code win_iocp_file_service::open( } } + if (disposition == OPEN_ALWAYS || (open_flags & file_base::append) != 0) { + LARGE_INTEGER distance, new_offset; + distance.QuadPart = 0; + if (::SetFilePointerEx(handle, distance, &new_offset, FILE_END)) + impl.offset_ = static_cast(new_offset.QuadPart); + else + { + DWORD last_error = ::GetLastError(); + ::CloseHandle(handle); + ec.assign(last_error, asio::error::get_system_category()); + ASIO_ERROR_LOCATION(ec); + return ec; + } + } + handle_service_.assign(impl, handle, ec); if (ec) ::CloseHandle(handle); - impl.offset_ = 0; ASIO_ERROR_LOCATION(ec); return ec; }