ex1) 드라이버 소스 심볼릭을 만들어 준다. Device Extension 버퍼에 값을 넣어준다.
#include <ntddk.h>
// Device Object 이름 - UNICODE 사용 "
// \\Device\\원하는 이름" - 반드시 이 규칙대로..
#define DEVICE_NAME L"\\Device\\WDM2" // 커널모드로 접근
// Symbolic Link 에 사용할 이름 "\\DosDevice\\원하는 이름"
#define DOS_NAME L"\\DosDevices\\Simple" // 유저 모드로 접근
// 보관하고 싶은 것을 구조체로 만든다. 사용자가 정의 가능..
typedef struct _DEVICE_EXTENSION
{
ULONG data;
} DEVICE_EXTENSION, *PDEVICE_EXTENSION;
VOID DriverUnload( IN PDRIVER_OBJECT pDriverObject)
{
UNICODE_STRING ustrDosName;
PDEVICE_OBJECT pDeviceObject;
PDEVICE_EXTENSION pDeviceExtension;
pDeviceObject = pDriverObject->DeviceObject;
pDeviceExtension = pDeviceObject->DeviceExtension;
DbgPrint("[Wdm2] DriverUnload : %d", pDeviceExtension->data );
RtlInitUnicodeString( &ustrDosName, DOS_NAME);
// Symbolic link 파괴 - 이름만 알면 된다.
IoDeleteSymbolicLink( &ustrDosName );
// Device Object 파괴 - Device Object 포인터 전달..
IoDeleteDevice( pDeviceObject );
}
NTSTATUS DriverEntry(IN PDRIVER_OBJECT pDriverObject, IN PUNICODE_STRING pRegistryPath)
{
NTSTATUS status = STATUS_SUCCESS;
// 구조체 이므로 함수를 사용하여 초기화 한다.
UNICODE_STRING ustrName;
UNICODE_STRING ustrDosName;
// 둘다 디바이스에 접근하기 위해 사용하는 포인터
PDEVICE_OBJECT pDeviceObject; // 원래 있는 구조체
PDEVICE_EXTENSION pDeviceExtension; // 사용자가 만든 구조체
DbgPrint("[WDM2] DriverEntry");
pDriverObject->DriverUnload = DriverUnload;
// 문자열을 초기화 한다. 결국은 strcpy()
RtlInitUnicodeString( &ustrName, DEVICE_NAME );
RtlInitUnicodeString( &ustrDosName, DOS_NAME );
// Device Object 를 장치당 1개씩 만들어야 한다.
// 하지만 하드웨어와 관련 없는 경우... User와 통신하기 위해 1개만 만든다.
status = IoCreateDevice( pDriverObject, // 드라이버 Object( 함수 제공 )
sizeof( DEVICE_EXTENSION), // Device EXTENSION 크기
&ustrName, // 이름
FILE_DEVICE_UNKNOWN,// 종류(마우스,키보드등등), 범용드라이버(UNKNOWN)
0,
TRUE, // H/W 관련..
&pDeviceObject); // 완성된 구조체의 주소가 이리로 온다.
DbgPrint( "address of DeviceObject : %p", pDeviceObject );
if ( ! NT_SUCCESS( status ) )
{
DbgPrint("[WDM2] Error IoCreateDevice");
return status;
}
// 테스트를 위한 코드..
pDeviceExtension = pDeviceObject->DeviceExtension;
pDeviceExtension->data = 100;
// User Mode 에서 접근하기 위해 별명(Symbolic link) 를 제공한다.
// 디바이스 오브젝트의 별명을 하나 준다.
status = IoCreateSymbolicLink( &ustrDosName, &ustrName);
if ( ! NT_SUCCESS( status ) )
{
DbgPrint("[WDM2] Error IoCreateSymbolicLink");
// 항상 나갈때는 삭제하고 가야한다. 드라이버는 위험하므로 꼭 지키자..
IoDeleteDevice( pDeviceObject );
}
return status;
}