Nice to see somebody filling in the gaps like this. A few nits based on a superficial reading: CopyFileA leaks a string. (I know, it did before your change, too.) copy_file_open_dest's interface comment has the wrong name. + for(i = 0; i < sizeof(flags) / sizeof(flags[0]); i++) + { + if(for_write) { Please use the same whitespace conventions as in the rest of the file (in particular, leave a space after keywords like for and if). + if ((h1 = copy_file_open_source(source, copyFlags & COPY_FILE_OPEN_SOURCE_FOR_WRITE)) == INVALID_HANDLE_VALUE) That line's too long... try to keep them under 80 chars. + // FIXME: total_file_size should include the sum of all streams Use C comments, not C++ comments. + DWORD result = progressRoutine(total_file_size, total_bytes_transferred, stream_size, stream_bytes_transferred, + stream_number, CALLBACK_STREAM_SWITCH, h1, h2, appData); Another instance of line longer than 80 chars. (You have several.) You don't have a conformance test, nor was there one for CopyFile. Maybe you should consider writing one, and making sure it passes both on Wine and Windows. Say, what app is this for? - Dan