Some time ago I wrote a small Win32 test application which did nothing else than creating an event to be used to synchronize between two processes. Coming back I was stunned by the fact that the process with CreateEvent
would return with error 5 (access denied), even when run as adminstrator.
ghWriteEvent = CreateEvent(
NULL, // default security attributes
FALSE, // auto-reset event
FALSE, // initial state is nonsignaled
TEXT("Global\\WriteEvent") // object name
);
if (ghWriteEvent == NULL)
{
printf("CreateEvent failed (%d)\n", GetLastError());
return 1;
}
After some debugging I decided to change the events' name and suddenly it worked. By chance I decided to look at the event creation/deletion in WinObj and I saw why it failed: there already was an event called WriteEvent
under \BaseNamedObjects
.
What could I have possibly done to make a named event persistent across reboots and more importantly, how can I get rid of it?
Edit: It seems some other application creates WriteEvent
in global namespace before my app has a chance to do so. The (now) obvious workaround is to use some unique name or to use a GUID or whatever to avoid name collision.
CodePudding user response:
When CreateEventW
fails for a named object with error code ERROR_ACCESS_DENIED
then that usually means that someone else created an event with that name already. In this case the system attempts to open the event object with EVENT_ALL_ACCESS
. When this access mode is incompatible with the ACLs of the calling thread the API call fails with ERROR_ACCESS_DENIED
.
To work around this you will need to come up with a unique name for the event object. A common approach is to use the string representation of a GUID for the name. You can generate a GUID using the guidgen.exe tool from a Visual Studio Developer Command prompt.