Introduction
Sometimes, we need to log some behavior of our code. When the program goes wrong, we could know the reason quickly, so someone would write a Logger, but we have a better choice, the windows EventLog service.
Background
Be familiar with windows DLL, and know how to create the DLL project.
Using the Code
First, we need a resource_only DLL file, we can create a DLL project using VC 2005, and the entry point (EventMsg.cpp) is as follows:
#include "stdafx.h"
#ifdef _MANAGED
#pragma managed(push, off)
#endif
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
return TRUE;
}
#ifdef _MANAGED
#pragma managed(pop)
#endif
We should include a MC file which defines the message ID, message SymbolicName, etc. I have written one just for a demo, mymsg.mc.
MessageIdTypedef=DWORD
SeverityNames=(Success=0x0:STATUS_SEVERITY_SUCCESS
Informational=0x1:STATUS_SEVERITY_INFORMATIONAL
Warning=0x2:STATUS_SEVERITY_WARNING
Error=0x3:STATUS_SEVERITY_ERROR
)
FacilityNames=(System=0x0:FACILITY_SYSTEM
Runtime=0x2:FACILITY_RUNTIME
Stubs=0x3:FACILITY_STUBS
Io=0x4:FACILITY_IO_ERROR_CODE
)
LanguageNames=(English=0x409:MSG00409)
MessageId=0x1
Severity=Error
Facility=Runtime
SymbolicName=MSG_BAD_ERROR1
Language=English
error one..
MessageId=0x2
Severity=Warning
Facility=Io
SymbolicName=MSG_BAD_ERROR2
Language=English
error two..
MessageId=0x3
Severity=Success
Facility=System
SymbolicName=MSG_BAD_ERROR3
Language=English
error three.
Now, we should compile it using cl.exe first.
cl -fo EventMsg.cpp
Maybe cl
would complain about something, but take it easy, anyhow we get EventMsg.obj
, that's enough. Then we compile mymsg.mc.
mc mymsg.mc
And we get mymsg.rc and mymsg.h (this file will be used by the Client).
rc -r -fo mymsg.res mymsg.rc
At last we link mymsg.res with EventMsg.obj.
link -dll -out:mymsg.dll EventMsg.obj mymsg.res
We have got the resource_only DLL now, the mymsg.dll file. Then we register it. I just write it to registry by hand, and you can refine this behavior. :)
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Eventlog\Application\MyApp
Create two KEYs under MyApp Item, one is EventMessageFile
(STRING
).
%SystemRoot%\System32\mymsg.dll
The other is TypeSupported
(DWORD
).
0x0000001f
Second, we should write a Client to use EventLog
:
#include "stdafx.h"
#include "Windows.h"
#include "mymsg.h"
#include "stdlib.h"
void ReportOneEvent(LPCSTR szMsg)
{
HANDLE h = RegisterEventSource(NULL, "MyApp");
if(h == NULL)
printf("register source error");
if (!ReportEvent(h,
EVENTLOG_ERROR_TYPE,
6,
MSG_BAD_ERROR3, NULL,
1,
strlen(szMsg),
&szMsg, (void*)szMsg))
printf("event report error");
DeregisterEventSource(h);
}
int _tmain(int argc, _TCHAR* argv[])
{
ReportOneEvent("event test");
return 0;
}
You could check it out with System Tools->Event Viewer.
Points of Interest
We can dig deeper into ReportEvent
, e.g.: the third parameter WORD
wCategory, we could view different categories using Event View by setting the parameter.
History
- 2009/01/17 version 1.0.0.2