2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS kernel
4 * FILE: drivers/net/afd/afd/main.c
5 * PURPOSE: Ancillary functions driver
6 * PROGRAMMER: Art Yerkes (ayerkes@speakeasy.net)
10 * Suggestions: Uniform naming (AfdXxx)
16 #include "tdi_proto.h"
22 /* See debug.h for debug/trace constants */
23 //DWORD DebugTraceLevel = DEBUG_ULTRA;
24 DWORD DebugTraceLevel
= 0;
28 void OskitDumpBuffer( PCHAR Data
, UINT Len
) {
31 for( i
= 0; i
< Len
; i
++ ) {
32 if( i
&& !(i
& 0xf) ) DbgPrint( "\n" );
33 if( !(i
& 0xf) ) DbgPrint( "%08x: ", (UINT
)(Data
+ i
) );
34 DbgPrint( " %02x", Data
[i
] & 0xff );
42 DriverEntry(PDRIVER_OBJECT DriverObject
, PUNICODE_STRING RegistryPath
);
45 AfdCreateSocket(PDEVICE_OBJECT DeviceObject
, PIRP Irp
,
46 PIO_STACK_LOCATION IrpSp
) {
48 PFILE_OBJECT FileObject
;
49 PAFD_DEVICE_EXTENSION DeviceExt
;
50 PFILE_FULL_EA_INFORMATION EaInfo
;
51 PAFD_CREATE_PACKET ConnectInfo
= NULL
;
53 PWCHAR EaInfoValue
= NULL
;
55 NTSTATUS Status
= STATUS_SUCCESS
;
57 AFD_DbgPrint(MID_TRACE
,
58 ("AfdCreate(DeviceObject %p Irp %p)\n", DeviceObject
, Irp
));
60 DeviceExt
= DeviceObject
->DeviceExtension
;
61 FileObject
= IrpSp
->FileObject
;
62 Disposition
= (IrpSp
->Parameters
.Create
.Options
>> 24) & 0xff;
64 Irp
->IoStatus
.Information
= 0;
66 EaInfo
= Irp
->AssociatedIrp
.SystemBuffer
;
69 ConnectInfo
= (PAFD_CREATE_PACKET
)(EaInfo
->EaName
+ EaInfo
->EaNameLength
+ 1);
70 EaInfoValue
= (PWCHAR
)(((PCHAR
)ConnectInfo
) + sizeof(AFD_CREATE_PACKET
));
72 EaLength
= sizeof(FILE_FULL_EA_INFORMATION
) +
73 EaInfo
->EaNameLength
+
74 EaInfo
->EaValueLength
;
76 AFD_DbgPrint(MID_TRACE
,("EaInfo: %x, EaInfoValue: %x\n",
77 EaInfo
, EaInfoValue
));
80 AFD_DbgPrint(MID_TRACE
,("About to allocate the new FCB\n"));
82 FCB
= ExAllocatePool(NonPagedPool
, sizeof(AFD_FCB
));
84 Irp
->IoStatus
.Status
= STATUS_NO_MEMORY
;
85 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
86 return STATUS_NO_MEMORY
;
89 AFD_DbgPrint(MID_TRACE
,("Initializing the new FCB @ %x (FileObject %x Flags %x)\n", FCB
, FileObject
, ConnectInfo
? ConnectInfo
->EndpointFlags
: 0));
91 RtlZeroMemory( FCB
, sizeof( *FCB
) );
93 FCB
->Flags
= ConnectInfo
? ConnectInfo
->EndpointFlags
: 0;
94 FCB
->GroupID
= ConnectInfo
? ConnectInfo
->GroupID
: 0;
95 FCB
->GroupType
= 0; /* FIXME */
96 FCB
->State
= SOCKET_STATE_CREATED
;
97 FCB
->FileObject
= FileObject
;
98 FCB
->DeviceExt
= DeviceExt
;
99 FCB
->Recv
.Size
= DEFAULT_RECEIVE_WINDOW_SIZE
;
100 FCB
->Send
.Size
= DEFAULT_SEND_WINDOW_SIZE
;
101 FCB
->AddressFile
.Handle
= INVALID_HANDLE_VALUE
;
102 FCB
->Connection
.Handle
= INVALID_HANDLE_VALUE
;
104 KeInitializeSpinLock( &FCB
->SpinLock
);
105 ExInitializeFastMutex( &FCB
->Mutex
);
106 KeInitializeEvent( &FCB
->StateLockedEvent
, NotificationEvent
, FALSE
);
108 for( i
= 0; i
< MAX_FUNCTIONS
; i
++ ) {
109 InitializeListHead( &FCB
->PendingIrpList
[i
] );
112 InitializeListHead( &FCB
->DatagramList
);
113 InitializeListHead( &FCB
->PendingConnections
);
115 AFD_DbgPrint(MID_TRACE
,("%x: Checking command channel\n", FCB
));
118 FCB
->TdiDeviceName
.Length
= ConnectInfo
->SizeOfTransportName
;
119 FCB
->TdiDeviceName
.MaximumLength
= FCB
->TdiDeviceName
.Length
;
120 FCB
->TdiDeviceName
.Buffer
=
121 ExAllocatePool( NonPagedPool
, FCB
->TdiDeviceName
.Length
);
123 if( !FCB
->TdiDeviceName
.Buffer
) {
125 AFD_DbgPrint(MID_TRACE
,("Could not copy target string\n"));
126 Irp
->IoStatus
.Status
= STATUS_NO_MEMORY
;
127 IoCompleteRequest( Irp
, IO_NETWORK_INCREMENT
);
128 return STATUS_NO_MEMORY
;
131 RtlCopyMemory( FCB
->TdiDeviceName
.Buffer
,
132 ConnectInfo
->TransportName
,
133 FCB
->TdiDeviceName
.Length
);
135 AFD_DbgPrint(MID_TRACE
,("Success: %s %wZ\n",
136 EaInfo
->EaName
, &FCB
->TdiDeviceName
));
138 AFD_DbgPrint(MID_TRACE
,("Success: Control connection\n"));
141 FileObject
->FsContext
= FCB
;
143 /* It seems that UDP sockets are writable from inception */
144 if( FCB
->Flags
& SGID_CONNECTIONLESS
) {
145 AFD_DbgPrint(MID_TRACE
,("Packet oriented socket\n"));
146 /* Allocate our backup buffer */
147 FCB
->Recv
.Window
= ExAllocatePool( NonPagedPool
, FCB
->Recv
.Size
);
148 if( !FCB
->Recv
.Window
) Status
= STATUS_NO_MEMORY
;
149 if( NT_SUCCESS(Status
) )
151 FCB
->Send
.Window
= ExAllocatePool( NonPagedPool
, FCB
->Send
.Size
);
152 if( !FCB
->Send
.Window
) {
153 if( FCB
->Recv
.Window
) ExFreePool( FCB
->Recv
.Window
);
154 Status
= STATUS_NO_MEMORY
;
157 /* A datagram socket is always sendable */
158 FCB
->PollState
|= AFD_EVENT_SEND
;
159 PollReeval( FCB
->DeviceExt
, FCB
->FileObject
);
162 if( !NT_SUCCESS(Status
) ) {
163 if( FCB
->TdiDeviceName
.Buffer
) ExFreePool( FCB
->TdiDeviceName
.Buffer
);
165 FileObject
->FsContext
= NULL
;
168 Irp
->IoStatus
.Status
= Status
;
169 IoCompleteRequest( Irp
, IO_NETWORK_INCREMENT
);
174 static NTSTATUS NTAPI
175 AfdCleanupSocket(PDEVICE_OBJECT DeviceObject
, PIRP Irp
,
176 PIO_STACK_LOCATION IrpSp
)
178 PFILE_OBJECT FileObject
= IrpSp
->FileObject
;
179 PAFD_FCB FCB
= FileObject
->FsContext
;
180 PLIST_ENTRY CurrentEntry
, NextEntry
;
184 if( !SocketAcquireStateLock( FCB
) ) return LostSocket(Irp
);
186 for (Function
= 0; Function
< MAX_FUNCTIONS
; Function
++)
188 CurrentEntry
= FCB
->PendingIrpList
[Function
].Flink
;
189 while (CurrentEntry
!= &FCB
->PendingIrpList
[Function
])
191 NextEntry
= CurrentEntry
->Flink
;
192 CurrentIrp
= CONTAINING_RECORD(CurrentEntry
, IRP
, Tail
.Overlay
.ListEntry
);
194 /* The cancel routine will remove the IRP from the list */
195 IoCancelIrp(CurrentIrp
);
197 CurrentEntry
= NextEntry
;
201 KillSelectsForFCB( FCB
->DeviceExt
, FileObject
, FALSE
);
203 return UnlockAndMaybeComplete(FCB
, STATUS_SUCCESS
, Irp
, 0);
206 static NTSTATUS NTAPI
207 AfdCloseSocket(PDEVICE_OBJECT DeviceObject
, PIRP Irp
,
208 PIO_STACK_LOCATION IrpSp
)
210 PFILE_OBJECT FileObject
= IrpSp
->FileObject
;
211 PAFD_FCB FCB
= FileObject
->FsContext
;
213 PAFD_IN_FLIGHT_REQUEST InFlightRequest
[IN_FLIGHT_REQUESTS
];
215 AFD_DbgPrint(MID_TRACE
,
216 ("AfdClose(DeviceObject %p Irp %p)\n", DeviceObject
, Irp
));
218 if( !SocketAcquireStateLock( FCB
) ) return STATUS_FILE_CLOSED
;
220 FCB
->State
= SOCKET_STATE_CLOSED
;
221 FCB
->PollState
= AFD_EVENT_CLOSE
;
222 PollReeval( FCB
->DeviceExt
, FCB
->FileObject
);
224 InFlightRequest
[0] = &FCB
->ListenIrp
;
225 InFlightRequest
[1] = &FCB
->ReceiveIrp
;
226 InFlightRequest
[2] = &FCB
->SendIrp
;
227 InFlightRequest
[3] = &FCB
->ConnectIrp
;
229 /* Cancel our pending requests */
230 for( i
= 0; i
< IN_FLIGHT_REQUESTS
; i
++ ) {
231 if( InFlightRequest
[i
]->InFlightRequest
) {
232 AFD_DbgPrint(MID_TRACE
,("Cancelling in flight irp %d (%x)\n",
233 i
, InFlightRequest
[i
]->InFlightRequest
));
234 IoCancelIrp(InFlightRequest
[i
]->InFlightRequest
);
238 KillSelectsForFCB( FCB
->DeviceExt
, FileObject
, FALSE
);
240 SocketStateUnlock( FCB
);
242 if( FCB
->EventSelect
)
243 ObDereferenceObject( FCB
->EventSelect
);
246 ExFreePool( FCB
->Context
);
248 if( FCB
->Recv
.Window
)
249 ExFreePool( FCB
->Recv
.Window
);
251 if( FCB
->Send
.Window
)
252 ExFreePool( FCB
->Send
.Window
);
254 if( FCB
->AddressFrom
)
255 ExFreePool( FCB
->AddressFrom
);
257 if( FCB
->LocalAddress
)
258 ExFreePool( FCB
->LocalAddress
);
260 if( FCB
->RemoteAddress
)
261 ExFreePool( FCB
->RemoteAddress
);
263 if( FCB
->Connection
.Object
)
264 ObDereferenceObject(FCB
->Connection
.Object
);
266 if( FCB
->AddressFile
.Object
)
267 ObDereferenceObject(FCB
->AddressFile
.Object
);
269 if( FCB
->AddressFile
.Handle
!= INVALID_HANDLE_VALUE
)
271 if (ZwClose(FCB
->AddressFile
.Handle
) == STATUS_INVALID_HANDLE
)
273 DbgPrint("INVALID ADDRESS FILE HANDLE VALUE: %x %x\n", FCB
->AddressFile
.Handle
, FCB
->AddressFile
.Object
);
277 if( FCB
->Connection
.Handle
!= INVALID_HANDLE_VALUE
)
279 if (ZwClose(FCB
->Connection
.Handle
) == STATUS_INVALID_HANDLE
)
281 DbgPrint("INVALID CONNECTION HANDLE VALUE: %x %x\n", FCB
->Connection
.Handle
, FCB
->Connection
.Object
);
285 if( FCB
->TdiDeviceName
.Buffer
)
286 ExFreePool(FCB
->TdiDeviceName
.Buffer
);
290 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
291 Irp
->IoStatus
.Information
= 0;
292 IoCompleteRequest(Irp
, IO_NETWORK_INCREMENT
);
294 AFD_DbgPrint(MID_TRACE
, ("Returning success.\n"));
296 return STATUS_SUCCESS
;
299 static NTSTATUS NTAPI
300 AfdDisconnect(PDEVICE_OBJECT DeviceObject
, PIRP Irp
,
301 PIO_STACK_LOCATION IrpSp
) {
302 PFILE_OBJECT FileObject
= IrpSp
->FileObject
;
303 PAFD_FCB FCB
= FileObject
->FsContext
;
304 PAFD_DISCONNECT_INFO DisReq
;
305 IO_STATUS_BLOCK Iosb
;
306 PTDI_CONNECTION_INFORMATION ConnInfo
;
310 if( !SocketAcquireStateLock( FCB
) ) return LostSocket( Irp
);
312 if( !(DisReq
= LockRequest( Irp
, IrpSp
)) )
313 return UnlockAndMaybeComplete( FCB
, STATUS_NO_MEMORY
,
316 if (NULL
== FCB
->RemoteAddress
)
322 Status
= TdiBuildNullConnectionInfo
323 ( &ConnInfo
, FCB
->RemoteAddress
->Address
[0].AddressType
);
325 if( !NT_SUCCESS(Status
) || !ConnInfo
)
326 return UnlockAndMaybeComplete( FCB
, STATUS_NO_MEMORY
,
330 if( DisReq
->DisconnectType
& AFD_DISCONNECT_SEND
)
331 Flags
|= TDI_DISCONNECT_RELEASE
;
332 if( DisReq
->DisconnectType
& AFD_DISCONNECT_RECV
||
333 DisReq
->DisconnectType
& AFD_DISCONNECT_ABORT
)
334 Flags
|= TDI_DISCONNECT_ABORT
;
336 Status
= TdiDisconnect( FCB
->Connection
.Object
,
345 if (ConnInfo
) ExFreePool( ConnInfo
);
347 FCB
->PollState
|= AFD_EVENT_DISCONNECT
;
348 PollReeval( FCB
->DeviceExt
, FCB
->FileObject
);
350 return UnlockAndMaybeComplete( FCB
, Status
, Irp
, 0 );
353 static NTSTATUS NTAPI
354 AfdDispatch(PDEVICE_OBJECT DeviceObject
, PIRP Irp
)
356 PIO_STACK_LOCATION IrpSp
= IoGetCurrentIrpStackLocation(Irp
);
357 NTSTATUS Status
= STATUS_SUCCESS
;
359 PFILE_OBJECT FileObject
= IrpSp
->FileObject
;
362 AFD_DbgPrint(MID_TRACE
,("AfdDispatch: %d\n", IrpSp
->MajorFunction
));
363 if( IrpSp
->MajorFunction
!= IRP_MJ_CREATE
) {
364 AFD_DbgPrint(MID_TRACE
,("FO %x, IrpSp->FO %x\n",
365 FileObject
, IrpSp
->FileObject
));
366 ASSERT(FileObject
== IrpSp
->FileObject
);
369 Irp
->IoStatus
.Information
= 0;
371 switch(IrpSp
->MajorFunction
)
373 /* opening and closing handles to the device */
375 /* Mostly borrowed from the named pipe file system */
376 return AfdCreateSocket(DeviceObject
, Irp
, IrpSp
);
379 /* Ditto the borrowing */
380 return AfdCloseSocket(DeviceObject
, Irp
, IrpSp
);
383 return AfdCleanupSocket(DeviceObject
, Irp
, IrpSp
);
387 return AfdConnectedSocketWriteData( DeviceObject
, Irp
, IrpSp
, TRUE
);
391 return AfdConnectedSocketReadData( DeviceObject
, Irp
, IrpSp
, TRUE
);
393 case IRP_MJ_DEVICE_CONTROL
:
395 switch( IrpSp
->Parameters
.DeviceIoControl
.IoControlCode
) {
397 return AfdBindSocket( DeviceObject
, Irp
, IrpSp
);
399 case IOCTL_AFD_CONNECT
:
400 return AfdStreamSocketConnect( DeviceObject
, Irp
, IrpSp
);
402 case IOCTL_AFD_START_LISTEN
:
403 return AfdListenSocket( DeviceObject
, Irp
, IrpSp
);
406 return AfdConnectedSocketReadData( DeviceObject
, Irp
, IrpSp
,
409 case IOCTL_AFD_SELECT
:
410 return AfdSelect( DeviceObject
, Irp
, IrpSp
);
412 case IOCTL_AFD_EVENT_SELECT
:
413 return AfdEventSelect( DeviceObject
, Irp
, IrpSp
);
415 case IOCTL_AFD_ENUM_NETWORK_EVENTS
:
416 return AfdEnumEvents( DeviceObject
, Irp
, IrpSp
);
418 case IOCTL_AFD_RECV_DATAGRAM
:
419 return AfdPacketSocketReadData( DeviceObject
, Irp
, IrpSp
);
422 return AfdConnectedSocketWriteData( DeviceObject
, Irp
, IrpSp
,
425 case IOCTL_AFD_SEND_DATAGRAM
:
426 return AfdPacketSocketWriteData( DeviceObject
, Irp
, IrpSp
);
428 case IOCTL_AFD_GET_INFO
:
429 return AfdGetInfo( DeviceObject
, Irp
, IrpSp
);
431 case IOCTL_AFD_SET_INFO
:
432 return AfdSetInfo( DeviceObject
, Irp
, IrpSp
);
434 case IOCTL_AFD_GET_CONTEXT
:
435 return AfdGetContext( DeviceObject
, Irp
, IrpSp
);
437 case IOCTL_AFD_SET_CONTEXT
:
438 return AfdSetContext( DeviceObject
, Irp
, IrpSp
);
440 case IOCTL_AFD_WAIT_FOR_LISTEN
:
441 return AfdWaitForListen( DeviceObject
, Irp
, IrpSp
);
443 case IOCTL_AFD_ACCEPT
:
444 return AfdAccept( DeviceObject
, Irp
, IrpSp
);
446 case IOCTL_AFD_DISCONNECT
:
447 return AfdDisconnect( DeviceObject
, Irp
, IrpSp
);
449 case IOCTL_AFD_GET_SOCK_NAME
:
450 return AfdGetSockName( DeviceObject
, Irp
, IrpSp
);
452 case IOCTL_AFD_GET_PEER_NAME
:
453 return AfdGetPeerName( DeviceObject
, Irp
, IrpSp
);
455 case IOCTL_AFD_GET_TDI_HANDLES
:
456 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_GET_TDI_HANDLES\n"));
459 case IOCTL_AFD_SET_CONNECT_DATA
:
460 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_CONNECT_DATA\n"));
463 case IOCTL_AFD_SET_CONNECT_OPTIONS
:
464 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_CONNECT_OPTIONS\n"));
467 case IOCTL_AFD_SET_DISCONNECT_DATA
:
468 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_DISCONNECT_DATA\n"));
471 case IOCTL_AFD_SET_DISCONNECT_OPTIONS
:
472 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_DISCONNECT_OPTIONS\n"));
475 case IOCTL_AFD_GET_CONNECT_DATA
:
476 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_GET_CONNECT_DATA\n"));
479 case IOCTL_AFD_GET_CONNECT_OPTIONS
:
480 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_GET_CONNECT_OPTIONS\n"));
483 case IOCTL_AFD_GET_DISCONNECT_DATA
:
484 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_GET_DISCONNECT_DATA\n"));
487 case IOCTL_AFD_GET_DISCONNECT_OPTIONS
:
488 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_GET_DISCONNECT_OPTIONS\n"));
491 case IOCTL_AFD_SET_CONNECT_DATA_SIZE
:
492 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_CONNECT_DATA_SIZE\n"));
495 case IOCTL_AFD_SET_CONNECT_OPTIONS_SIZE
:
496 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_CONNECT_OPTIONS_SIZE\n"));
499 case IOCTL_AFD_SET_DISCONNECT_DATA_SIZE
:
500 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_DISCONNECT_DATA_SIZE\n"));
503 case IOCTL_AFD_SET_DISCONNECT_OPTIONS_SIZE
:
504 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_SET_DISCONNECT_OPTIONS_SIZE\n"));
507 case IOCTL_AFD_DEFER_ACCEPT
:
508 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_DEFER_ACCEPT\n"));
511 case IOCTL_AFD_GET_PENDING_CONNECT_DATA
:
512 AFD_DbgPrint(MIN_TRACE
, ("IOCTL_AFD_GET_PENDING_CONNECT_DATA\n"));
516 Status
= STATUS_NOT_IMPLEMENTED
;
517 AFD_DbgPrint(MIN_TRACE
, ("Unknown IOCTL (0x%x)\n",
518 IrpSp
->Parameters
.DeviceIoControl
.
525 /* unsupported operations */
528 Status
= STATUS_NOT_IMPLEMENTED
;
529 AFD_DbgPrint(MIN_TRACE
,
530 ("Irp: Unknown Major code was %x\n",
531 IrpSp
->MajorFunction
));
536 AFD_DbgPrint(MID_TRACE
, ("Returning %x\n", Status
));
537 Irp
->IoStatus
.Status
= Status
;
538 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
544 AfdCancelHandler(PDEVICE_OBJECT DeviceObject
,
547 PIO_STACK_LOCATION IrpSp
= IoGetCurrentIrpStackLocation(Irp
);
548 PFILE_OBJECT FileObject
= IrpSp
->FileObject
;
549 PAFD_FCB FCB
= FileObject
->FsContext
;
551 PAFD_RECV_INFO RecvReq
;
552 PAFD_SEND_INFO SendReq
;
553 PLIST_ENTRY CurrentEntry
;
555 PAFD_DEVICE_EXTENSION DeviceExt
= DeviceObject
->DeviceExtension
;
557 PAFD_ACTIVE_POLL Poll
;
558 PAFD_POLL_INFO PollReq
;
560 IoReleaseCancelSpinLock(Irp
->CancelIrql
);
562 if (!SocketAcquireStateLock(FCB
))
565 ASSERT(IrpSp
->MajorFunction
== IRP_MJ_DEVICE_CONTROL
);
567 switch (IrpSp
->Parameters
.DeviceIoControl
.IoControlCode
)
570 RecvReq
= IrpSp
->Parameters
.DeviceIoControl
.Type3InputBuffer
;
571 UnlockBuffers(RecvReq
->BufferArray
, RecvReq
->BufferCount
, FALSE
);
574 case IOCTL_AFD_RECV_DATAGRAM
:
575 Function
= FUNCTION_RECV
;
579 SendReq
= IrpSp
->Parameters
.DeviceIoControl
.Type3InputBuffer
;
580 UnlockBuffers(SendReq
->BufferArray
, SendReq
->BufferCount
, FALSE
);
583 case IOCTL_AFD_SEND_DATAGRAM
:
584 Function
= FUNCTION_SEND
;
587 case IOCTL_AFD_CONNECT
:
588 Function
= FUNCTION_CONNECT
;
591 case IOCTL_AFD_WAIT_FOR_LISTEN
:
592 Function
= FUNCTION_PREACCEPT
;
595 case IOCTL_AFD_SELECT
:
596 KeAcquireSpinLock(&DeviceExt
->Lock
, &OldIrql
);
598 CurrentEntry
= DeviceExt
->Polls
.Flink
;
599 while (CurrentEntry
!= &DeviceExt
->Polls
)
601 Poll
= CONTAINING_RECORD(CurrentEntry
, AFD_ACTIVE_POLL
, ListEntry
);
602 CurrentIrp
= Poll
->Irp
;
603 PollReq
= CurrentIrp
->AssociatedIrp
.SystemBuffer
;
605 if (CurrentIrp
== Irp
)
607 ZeroEvents(PollReq
->Handles
, PollReq
->HandleCount
);
608 SignalSocket(Poll
, NULL
, PollReq
, STATUS_CANCELLED
);
613 CurrentEntry
= CurrentEntry
->Flink
;
617 KeReleaseSpinLock(&DeviceExt
->Lock
, OldIrql
);
619 /* IRP already completed by SignalSocket */
620 SocketStateUnlock(FCB
);
625 UnlockAndMaybeComplete(FCB
, STATUS_CANCELLED
, Irp
, 0);
629 CurrentEntry
= FCB
->PendingIrpList
[Function
].Flink
;
630 while (CurrentEntry
!= &FCB
->PendingIrpList
[Function
])
632 CurrentIrp
= CONTAINING_RECORD(CurrentEntry
, IRP
, Tail
.Overlay
.ListEntry
);
634 if (CurrentIrp
== Irp
)
636 RemoveEntryList(CurrentEntry
);
641 CurrentEntry
= CurrentEntry
->Flink
;
645 UnlockAndMaybeComplete(FCB
, STATUS_CANCELLED
, Irp
, 0);
649 AfdUnload(PDRIVER_OBJECT DriverObject
)
654 DriverEntry(PDRIVER_OBJECT DriverObject
, PUNICODE_STRING RegistryPath
)
656 PDEVICE_OBJECT DeviceObject
;
657 UNICODE_STRING wstrDeviceName
= RTL_CONSTANT_STRING(L
"\\Device\\Afd");
658 PAFD_DEVICE_EXTENSION DeviceExt
;
661 /* register driver routines */
662 DriverObject
->MajorFunction
[IRP_MJ_CLOSE
] = AfdDispatch
;
663 DriverObject
->MajorFunction
[IRP_MJ_CREATE
] = AfdDispatch
;
664 DriverObject
->MajorFunction
[IRP_MJ_CLEANUP
] = AfdDispatch
;
665 DriverObject
->MajorFunction
[IRP_MJ_WRITE
] = AfdDispatch
;
666 DriverObject
->MajorFunction
[IRP_MJ_READ
] = AfdDispatch
;
667 DriverObject
->MajorFunction
[IRP_MJ_DEVICE_CONTROL
] = AfdDispatch
;
668 DriverObject
->DriverUnload
= AfdUnload
;
670 Status
= IoCreateDevice
672 sizeof(AFD_DEVICE_EXTENSION
),
674 FILE_DEVICE_NAMED_PIPE
,
680 if(!NT_SUCCESS(Status
))
685 DeviceExt
= DeviceObject
->DeviceExtension
;
686 KeInitializeSpinLock( &DeviceExt
->Lock
);
687 InitializeListHead( &DeviceExt
->Polls
);
689 AFD_DbgPrint(MID_TRACE
,("Device created: object %x ext %x\n",
690 DeviceObject
, DeviceExt
));