From: Cameron Gutman Date: Sat, 5 Dec 2009 16:29:41 +0000 (+0000) Subject: [TCPIP] X-Git-Tag: backups/aicom-network-stable@46924^2^2~19 X-Git-Url: https://git.reactos.org/?p=reactos.git;a=commitdiff_plain;h=ab7bd8eb08d51c0f5e27696c441ceff91770e1e5 [TCPIP] - Implement TDI_QUERY_MAX_DATAGRAM_INFO [AFD] - Send TDI_QUERY_MAX_DATAGRAM_INFO to set our send/receive windows properly - Don't create a send window for a datagram socket because it is never used - Fixes dropping all packets with length > 16384 svn path=/branches/aicom-network-branch/; revision=44412 --- diff --git a/drivers/network/afd/afd/bind.c b/drivers/network/afd/afd/bind.c index d7504b8ca65..c574a75670e 100644 --- a/drivers/network/afd/afd/bind.c +++ b/drivers/network/afd/afd/bind.c @@ -32,6 +32,20 @@ NTSTATUS WarmSocketForBind( PAFD_FCB FCB ) { FCB->LocalAddress, &FCB->AddressFile.Handle, &FCB->AddressFile.Object ); + if (!NT_SUCCESS(Status)) + return Status; + + if (FCB->Flags & AFD_ENDPOINT_CONNECTIONLESS) + { + Status = TdiQueryMaxDatagramLength(FCB->AddressFile.Object, + &FCB->Recv.Size); + if (NT_SUCCESS(Status)) + { + FCB->Recv.Window = ExAllocatePool(PagedPool, FCB->Recv.Size); + if (!FCB->Recv.Window) + Status = STATUS_NO_MEMORY; + } + } AFD_DbgPrint(MID_TRACE,("Returning %x\n", Status)); @@ -69,10 +83,6 @@ AfdBindSocket(PDEVICE_OBJECT DeviceObject, PIRP Irp, if( FCB->Flags & AFD_ENDPOINT_CONNECTIONLESS ) { AFD_DbgPrint(MID_TRACE,("Calling TdiReceiveDatagram\n")); - FCB->Recv.Window = ExAllocatePool(PagedPool, FCB->Recv.Size); - if (!FCB->Recv.Window) - return UnlockAndMaybeComplete(FCB, STATUS_NO_MEMORY, Irp, 0); - Status = TdiReceiveDatagram ( &FCB->ReceiveIrp.InFlightRequest, FCB->AddressFile.Object, diff --git a/drivers/network/afd/afd/connect.c b/drivers/network/afd/afd/connect.c index 1da57e2ac4b..7ee3abaec57 100644 --- a/drivers/network/afd/afd/connect.c +++ b/drivers/network/afd/afd/connect.c @@ -211,6 +211,13 @@ NTSTATUS MakeSocketIntoConnection( PAFD_FCB FCB ) { ASSERT(!FCB->Recv.Window); ASSERT(!FCB->Send.Window); + Status = TdiQueryMaxDatagramLength(FCB->Connection.Object, + &FCB->Send.Size); + if (!NT_SUCCESS(Status)) + return Status; + + FCB->Recv.Size = FCB->Send.Size; + /* Allocate the receive area and start receiving */ FCB->Recv.Window = ExAllocatePool( PagedPool, FCB->Recv.Size ); diff --git a/drivers/network/afd/afd/main.c b/drivers/network/afd/afd/main.c index 10ebe9a5ae5..80fead13cc7 100644 --- a/drivers/network/afd/afd/main.c +++ b/drivers/network/afd/afd/main.c @@ -268,8 +268,6 @@ AfdCreateSocket(PDEVICE_OBJECT DeviceObject, PIRP Irp, FCB->State = SOCKET_STATE_CREATED; FCB->FileObject = FileObject; FCB->DeviceExt = DeviceExt; - FCB->Recv.Size = DEFAULT_RECEIVE_WINDOW_SIZE; - FCB->Send.Size = DEFAULT_SEND_WINDOW_SIZE; FCB->AddressFile.Handle = INVALID_HANDLE_VALUE; FCB->Connection.Handle = INVALID_HANDLE_VALUE; @@ -313,13 +311,10 @@ AfdCreateSocket(PDEVICE_OBJECT DeviceObject, PIRP Irp, /* It seems that UDP sockets are writable from inception */ if( FCB->Flags & AFD_ENDPOINT_CONNECTIONLESS ) { AFD_DbgPrint(MID_TRACE,("Packet oriented socket\n")); - FCB->Send.Window = ExAllocatePool( PagedPool, FCB->Send.Size ); - if (FCB->Send.Window) - { - /* A datagram socket is always sendable */ - FCB->PollState |= AFD_EVENT_SEND; - PollReeval( FCB->DeviceExt, FCB->FileObject ); - } else Status = STATUS_NO_MEMORY; + + /* A datagram socket is always sendable */ + FCB->PollState |= AFD_EVENT_SEND; + PollReeval( FCB->DeviceExt, FCB->FileObject ); } if( !NT_SUCCESS(Status) ) { diff --git a/drivers/network/afd/afd/tdi.c b/drivers/network/afd/afd/tdi.c index 7367e55c7fa..b6821b06c90 100644 --- a/drivers/network/afd/afd/tdi.c +++ b/drivers/network/afd/afd/tdi.c @@ -206,6 +206,56 @@ NTSTATUS TdiOpenAddressFile( return Status; } +NTSTATUS TdiQueryMaxDatagramLength( + PFILE_OBJECT FileObject, + PUINT MaxDatagramLength) +{ + PMDL Mdl; + PTDI_MAX_DATAGRAM_INFO Buffer; + NTSTATUS Status = STATUS_SUCCESS; + + Buffer = ExAllocatePool(NonPagedPool, sizeof(TDI_MAX_DATAGRAM_INFO)); + if (!Buffer) return STATUS_NO_MEMORY; + + Mdl = IoAllocateMdl(Buffer, sizeof(TDI_MAX_DATAGRAM_INFO), FALSE, FALSE, NULL); + if (!Mdl) + { + ExFreePool(Buffer); + return STATUS_NO_MEMORY; + } + + _SEH2_TRY + { + MmProbeAndLockPages(Mdl, KernelMode, IoModifyAccess); + } + _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) + { + Status = _SEH2_GetExceptionCode(); + } + _SEH2_END; + + if (!NT_SUCCESS(Status)) + { + IoFreeMdl(Mdl); + ExFreePool(Buffer); + return Status; + } + + Status = TdiQueryInformation(FileObject, + TDI_QUERY_MAX_DATAGRAM_INFO, + Mdl); + if (!NT_SUCCESS(Status)) + { + ExFreePool(Buffer); + return Status; + } + + *MaxDatagramLength = Buffer->MaxDatagramSize; + + ExFreePool(Buffer); + + return STATUS_SUCCESS; +} NTSTATUS TdiOpenConnectionEndpointFile( PUNICODE_STRING DeviceName, diff --git a/drivers/network/afd/include/afd.h b/drivers/network/afd/include/afd.h index c16afb6e7d3..6b5e875ec9b 100644 --- a/drivers/network/afd/include/afd.h +++ b/drivers/network/afd/include/afd.h @@ -108,9 +108,6 @@ typedef struct IPADDR_ENTRY { * for ancillary data on packet * requests. */ -#define DEFAULT_SEND_WINDOW_SIZE 16384 -#define DEFAULT_RECEIVE_WINDOW_SIZE 16384 - /* XXX This is a hack we should clean up later * We do this in order to get some storage for the locked handle table * Maybe I'll use some tail item in the irp instead */ @@ -412,6 +409,10 @@ NTSTATUS TdiSendDatagram( PIO_COMPLETION_ROUTINE CompletionRoutine, PVOID CompletionContext); +NTSTATUS TdiQueryMaxDatagramLength( + PFILE_OBJECT FileObject, + PUINT MaxDatagramLength); + /* write.c */ NTSTATUS NTAPI diff --git a/drivers/network/tcpip/tcpip/dispatch.c b/drivers/network/tcpip/tcpip/dispatch.c index c6f2d2a55e9..fe8d7664b88 100644 --- a/drivers/network/tcpip/tcpip/dispatch.c +++ b/drivers/network/tcpip/tcpip/dispatch.c @@ -761,6 +761,15 @@ NTSTATUS DispTdiQueryInformation( return TCPGetSockAddress( Endpoint, AddressInfo->RemoteAddress, TRUE ); } + + case TDI_QUERY_MAX_DATAGRAM_INFO: + { + PTDI_MAX_DATAGRAM_INFO MaxDatagramInfo = MmGetSystemAddressForMdl(Irp->MdlAddress); + + MaxDatagramInfo->MaxDatagramSize = 0xFFFF; + + return STATUS_SUCCESS; + } } return STATUS_NOT_IMPLEMENTED;