阅读:1027回复:4
这里人好多,有本事的人进来拿分!
告诉我怎么从驱动(SYS)里向应用程序(DLL)发消息或是直接调用CALLBACK之类的函数:
我的目的是想应用程序可以实时响应驱动里面发生的事件(实时的变化),我的驱动是1394的通讯,看了一下,好像有这么几种方法,WriteFile,ReadFile,DeviceIoControl,但好像都不能满足我的要求嘛 知道的请回答,谢了。得要领的送20分 |
|
|
沙发#
发布于:2002-07-03 09:19
可以用异步deviceiocontrol,然后发事件给app,可以参看 walter书的第九章.
|
|
|
板凳#
发布于:2002-07-03 09:21
告诉我怎么从驱动(SYS)里向应用程序(DLL)发消息或是直接调用CALLBACK之类的函数: 驱动和应用之间的通讯问题,好像已经有高手讨论过了。除了你说的,好像可以设置一个驱动和应用共享的event,具体的办法我计不住了 :) |
|
|
地板#
发布于:2002-07-03 09:46
告诉我怎么从驱动(SYS)里向应用程序(DLL)发消息或是直接调用CALLBACK之类的函数: 哈哈,找到了 Signaling an Application from a Kernel Mode Driver Sometimes a driver needs to signal an application. There are at least three ways to do this: Method 1 The application makes a DeviceIoControl to the driver. The driver returns STATUS_PENDING. When the event occurs, the driver completes the IRP. The thread returns from the DeviceIoControl call and handles the event. // sample class declaration class MyDevice : public KDevice { public: MyDevice(); VOID EventHandler(void); DEVMEMBER_DISPATCHERS DEVMEMBER_CANCELIRP (MyDevice, CancelSignalIrp); KIrp m_IrpToCompleteToSignalEvent; }; // Handler for Device Control requests NTSTATUS MyDevice::DeviceControl(KIrp I) { switch (I.IoctlCode()) { case MYDEVICE_IOCTL_SETUP_SIGNAL: CancelSpinLock::Acquire(); I.SetCancelRoutine(LinkTo(CancelSignalIrp)); m_IrpToCompleteToSignalEvent = I; CancelSpinLock::Release(); return STATUS_PENDING; break; . . . } } // cancel routine for the signal IRP VOID MyDevice::CancelSignalIrp(KIrp I) { m_IrpToCompleteToSignalEvent = KIrp(NULL); I.Information() = 0; CancelSpinLock::Release(I->CancelIrql); I.Complete(STATUS_CANCELLED); } // Routine that completes the IRP to signal the event // to the application. Not callable at IRQL > DISPATCH_LEVEL. VOID MyDevice::EventHandler(void) { KIrp I = m_IrpToCompleteToSignalEvent; m_IrpToCompleteToSignalEvent = KIrp(NULL); I.Information() = 0; I.Complete(STATUS_SUCCESS); } Method 2 The application creates an event object, and passes the handle to the driver via DeviceIoControl. The driver obtains an object pointer for the event, which it can then set or reset. Note that the thread handle is specific to the calling process. Therefore, this method can only be used for monolithic or highest level drivers. // sample class declaration class MyDevice : public KDevice { public: MyDevice(); VOID EventHandler(void); KEvent * m_pEventToSignal; }; // Handler for Device Control requests NTSTATUS MyDevice::DeviceControl(KIrp I) { switch (I.IoctlCode()) { case MYDEVICE_IOCTL_SETUP_SIGNAL: // app passes event handle in input buffer HANDLE hEvent = *(HANDLE*)I.IoctlBuffer(); m_pEventToSignal = new(NonPagedPool) KEvent(hEvent); NTSTATUS status = (m_pEventToSignal != NULL) : STATUS_SUCCESS ? STATUS_INSUFFICIENT_RESOURCES; return I.Complete(status); break; . . . } } // Routine signals the event to the application. // Not callable at IRQL > DISPATCH_LEVEL. VOID MyDevice::EventHandler(void) { m_pEventToSignal->Set(); // or Pulse } Method 3 Note: This method is not available in versions of Windows NT earlier than 4.0. Create a named event. #define APP_EVENT_NAME \"SynchEvent\" #define DRIVER_EVENT_NAME L\"\\\\BaseNamedObjects\\\\SynchEvent\" // Application code hEvent = OpenEvent(SYNCHRONIZE, FALSE, EVENT_NAME); // The driver must have already created the event in // order for this to succeed. If you want the app to // create the event, use CreateEvent instead of OpenEvent. // If the user is not privileged, it is required to // create the event in the application. // Driver Initialization Code KEvent* m_pSynchEvent = new (NonPagedPool) KEvent( KUstring(DRIVER_EVENT_NAME),SynchronizationEvent); m_pSynchEvent->Clear(); // initially signaled // The following code signals the event m_pSynchEvent->Set(); |
|
|
地下室#
发布于:2002-07-03 12:27
如果用在nt(nt4 2k xp .net),你可以考虑异步过程调用(APC),高效,快速...................
|
|