diff --git a/dlls/kernel32/file.c b/dlls/kernel32/file.c index ed97c5113a1..4e05c284211 100644 --- a/dlls/kernel32/file.c +++ b/dlls/kernel32/file.c @@ -1428,7 +1428,14 @@ HANDLE WINAPI CreateFileW( LPCWSTR filename, DWORD access, DWORD sharing, else SetLastError( RtlNtStatusToDosError(status) ); } - else SetLastError(0); + else + { + if ((creation == CREATE_ALWAYS && io.Information == FILE_OVERWRITTEN) || + (creation == OPEN_ALWAYS && io.Information == FILE_OPENED)) + SetLastError( ERROR_ALREADY_EXISTS ); + else + SetLastError( 0 ); + } RtlFreeUnicodeString( &nameW ); done: diff --git a/dlls/kernel32/tests/file.c b/dlls/kernel32/tests/file.c index d115a570c5e..cb3fc35150e 100644 --- a/dlls/kernel32/tests/file.c +++ b/dlls/kernel32/tests/file.c @@ -658,11 +658,39 @@ static void test_CreateFileA(void) ret = GetTempFileNameA(temp_path, prefix, 0, filename); ok(ret != 0, "GetTempFileNameA error %d\n", GetLastError()); + SetLastError(0xdeadbeef); hFile = CreateFileA(filename, GENERIC_READ, 0, NULL, CREATE_NEW, FILE_FLAG_RANDOM_ACCESS, 0); ok(hFile == INVALID_HANDLE_VALUE && GetLastError() == ERROR_FILE_EXISTS, "CREATE_NEW should fail if file exists and last error value should be ERROR_FILE_EXISTS\n"); + SetLastError(0xdeadbeef); + hFile = CreateFileA(filename, GENERIC_READ, FILE_SHARE_READ, NULL, + CREATE_ALWAYS, FILE_FLAG_RANDOM_ACCESS, 0); + ok(hFile != INVALID_HANDLE_VALUE && GetLastError() == ERROR_ALREADY_EXISTS, + "hFile %p, last error %u\n", hFile, GetLastError()); + + CloseHandle(hFile); + + SetLastError(0xdeadbeef); + hFile = CreateFileA(filename, GENERIC_READ, FILE_SHARE_READ, NULL, + OPEN_ALWAYS, FILE_FLAG_RANDOM_ACCESS, 0); + ok(hFile != INVALID_HANDLE_VALUE && GetLastError() == ERROR_ALREADY_EXISTS, + "hFile %p, last error %u\n", hFile, GetLastError()); + + CloseHandle(hFile); + + ret = DeleteFileA(filename); + ok(ret, "DeleteFileA: error %d\n", GetLastError()); + + SetLastError(0xdeadbeef); + hFile = CreateFileA(filename, GENERIC_READ, FILE_SHARE_READ, NULL, + OPEN_ALWAYS, FILE_FLAG_RANDOM_ACCESS, 0); + ok(hFile != INVALID_HANDLE_VALUE && GetLastError() == 0, + "hFile %p, last error %u\n", hFile, GetLastError()); + + CloseHandle(hFile); + ret = DeleteFileA(filename); ok(ret, "DeleteFileA: error %d\n", GetLastError()); } @@ -686,11 +714,39 @@ static void test_CreateFileW(void) ret = GetTempFileNameW(temp_path, prefix, 0, filename); ok(ret != 0, "GetTempFileNameW error %d\n", GetLastError()); + SetLastError(0xdeadbeef); hFile = CreateFileW(filename, GENERIC_READ, 0, NULL, CREATE_NEW, FILE_FLAG_RANDOM_ACCESS, 0); ok(hFile == INVALID_HANDLE_VALUE && GetLastError() == ERROR_FILE_EXISTS, "CREATE_NEW should fail if file exists and last error value should be ERROR_FILE_EXISTS\n"); + SetLastError(0xdeadbeef); + hFile = CreateFileW(filename, GENERIC_READ, FILE_SHARE_READ, NULL, + CREATE_ALWAYS, FILE_FLAG_RANDOM_ACCESS, 0); + ok(hFile != INVALID_HANDLE_VALUE && GetLastError() == ERROR_ALREADY_EXISTS, + "hFile %p, last error %u\n", hFile, GetLastError()); + + CloseHandle(hFile); + + SetLastError(0xdeadbeef); + hFile = CreateFileW(filename, GENERIC_READ, FILE_SHARE_READ, NULL, + OPEN_ALWAYS, FILE_FLAG_RANDOM_ACCESS, 0); + ok(hFile != INVALID_HANDLE_VALUE && GetLastError() == ERROR_ALREADY_EXISTS, + "hFile %p, last error %u\n", hFile, GetLastError()); + + CloseHandle(hFile); + + ret = DeleteFileW(filename); + ok(ret, "DeleteFileW: error %d\n", GetLastError()); + + SetLastError(0xdeadbeef); + hFile = CreateFileW(filename, GENERIC_READ, FILE_SHARE_READ, NULL, + OPEN_ALWAYS, FILE_FLAG_RANDOM_ACCESS, 0); + ok(hFile != INVALID_HANDLE_VALUE && GetLastError() == 0, + "hFile %p, last error %u\n", hFile, GetLastError()); + + CloseHandle(hFile); + ret = DeleteFileW(filename); ok(ret, "DeleteFileW: error %d\n", GetLastError());