user2713021
user2713021

Reputation: 79

Failed to create a file in windows using createFile API

I am failing to create a file in windows using the CreateFile API, GetLastError returns the error code 80 which means the file exists, but actually the file was not existing.

hFile = CreateFile((LPCTSTR) FILEPATH,  // name of the write 
    GENERIC_READ|GENERIC_WRITE,         // open for writing
    0,                                  // do not share
    NULL,                               // default security 
    CREATE_ALWAYS,                      // create new file only 
    FILE_ATTRIBUTE_NORMAL,              // normal file
    NULL);                              // no attr. template
printf("GET LAST ERROR VALUE IS: %d\n", GetLastError());

What am I doing wrong?

Upvotes: 2

Views: 3810

Answers (2)

David Heffernan
David Heffernan

Reputation: 613451

Your error checking is wrong. The documentation says:

Return value

If the function succeeds, the return value is an open handle to the specified file, device, named pipe, or mail slot.

If the function fails, the return value is INVALID_HANDLE_VALUE. To get extended error information, call GetLastError.

In other words, failure is determined by the return value. You cannot use GetLastError to determine failure. You must check the return value and compare against INVALID_HANDLE_VALUE. When you do so I predict that you will find that the return value is not equal to INVALID_HANDLE_VALUE.


In fact, this API uses the last error value to convey extra information even when the function succeeds.

From the documentation of CREATE_ALWAYS:

If the specified file exists and is writable, the function overwrites the file, the function succeeds, and last-error code is set to ERROR_ALREADY_EXISTS (183).

And from the documentation of CREATE_NEW:

Creates a new file, only if it does not already exist. If the specified file exists, the function fails and the last-error code is set to ERROR_FILE_EXISTS (80).

And so on.

The golden rule, one that you must burn into your memory, is that error checking varies from function to function and that you must read the documentation from top to tail.


Note that I am rather sceptical of your (LPCTSTR) cast. That's just asking for trouble. If the path is the wrong type, the compiler will save you from yourself, unless you use that cast. That cast just tells the compiler to shut up. But here it knows better. That cast will allow you to pass ANSI text to a wide API and vice versa. You really should remove it.

Upvotes: 7

doctorlove
doctorlove

Reputation: 19282

GetLastError can cause trouble. Note the docs say

"If the function fails, the return value is INVALID_HANDLE_VALUE. To get extended error information, call GetLastError."

So, first, only call GetLastError if you get and INVALID_HANDLE_VALUE handle back from CreateFile.

Second, the last error code can be the , well, liertally, last error code - i.e. the most recent call may be OK, but something previously failed: again from the docs

"If the function is not documented to set the last-error code, the value returned by this function is simply the most recent last-error code to have been set; some functions set the last-error code to 0 on success and others do not."

Upvotes: 2

Related Questions