diff --git a/reactos/drivers/net/afd/afd/main.c b/reactos/drivers/net/afd/afd/main.c index 969cf2027a6..89689909701 100644 --- a/reactos/drivers/net/afd/afd/main.c +++ b/reactos/drivers/net/afd/afd/main.c @@ -1,4 +1,4 @@ -/* $Id: main.c,v 1.9 2004/11/12 09:27:02 arty Exp $ +/* $Id: main.c,v 1.10 2004/11/14 19:45:16 arty Exp $ * COPYRIGHT: See COPYING in the top level directory * PROJECT: ReactOS kernel * FILE: drivers/net/afd/afd/main.c @@ -22,8 +22,8 @@ extern NTSTATUS DDKAPI MmCopyFromCaller( PVOID Dst, PVOID Src, UINT Size ); /* See debug.h for debug/trace constants */ -DWORD DebugTraceLevel = DEBUG_ULTRA; -//DWORD DebugTraceLevel = 0; +//DWORD DebugTraceLevel = DEBUG_ULTRA; +DWORD DebugTraceLevel = 0; #endif /* DBG */ diff --git a/reactos/drivers/net/afd/afd/read.c b/reactos/drivers/net/afd/afd/read.c index 5674505922f..b04a5faafae 100644 --- a/reactos/drivers/net/afd/afd/read.c +++ b/reactos/drivers/net/afd/afd/read.c @@ -1,4 +1,4 @@ -/* $Id: read.c,v 1.8 2004/11/12 07:34:56 arty Exp $ +/* $Id: read.c,v 1.9 2004/11/14 19:45:16 arty Exp $ * COPYRIGHT: See COPYING in the top level directory * PROJECT: ReactOS kernel * FILE: drivers/net/afd/afd/read.c @@ -45,6 +45,7 @@ NTSTATUS TryToSatisfyRecvRequestFromBuffer( PAFD_FCB FCB, i, Map[i].BufferAddress, BytesToCopy)); + RtlCopyMemory( Map[i].BufferAddress, FCB->Recv.Window + FCB->Recv.BytesUsed, BytesToCopy ); @@ -100,7 +101,7 @@ NTSTATUS DDKAPI ReceiveComplete AFD_DbgPrint(MID_TRACE,("FCB %x Receive data waiting %d\n", FCB, FCB->Recv.Content)); - OskitDumpBuffer( FCB->Recv.Window, FCB->Recv.Content ); + /*OskitDumpBuffer( FCB->Recv.Window, FCB->Recv.Content );*/ Status = STATUS_SUCCESS; @@ -253,6 +254,9 @@ SatisfyPacketRecvRequest( PAFD_FCB FCB, PIRP Irp, BytesToCopy = MIN( RecvReq->BufferArray[0].len, BytesAvailable ); + AFD_DbgPrint(MID_TRACE,("BytesToCopy: %d len %d\n", BytesToCopy, + RecvReq->BufferArray[0].len)); + if( Map[0].Mdl ) { Map[0].BufferAddress = MmMapLockedPages( Map[0].Mdl, KernelMode ); @@ -260,6 +264,10 @@ SatisfyPacketRecvRequest( PAFD_FCB FCB, PIRP Irp, 0, Map[0].BufferAddress, BytesToCopy)); + + /* OskitDumpBuffer + ( FCB->Recv.Window + FCB->Recv.BytesUsed, BytesToCopy ); */ + RtlCopyMemory( Map[0].BufferAddress, FCB->Recv.Window + FCB->Recv.BytesUsed, BytesToCopy ); @@ -316,12 +324,12 @@ PacketSocketRecvComplete( while( NT_SUCCESS(Status) && !IsListEmpty( &FCB->DatagramList ) && - !IsListEmpty( &FCB->PendingIrpList[FUNCTION_RECV_DATAGRAM] ) ) { + !IsListEmpty( &FCB->PendingIrpList[FUNCTION_RECV] ) ) { ListEntry = RemoveHeadList( &FCB->DatagramList ); DatagramRecv = CONTAINING_RECORD( ListEntry, AFD_STORED_DATAGRAM, ListEntry ); ListEntry = RemoveHeadList - ( &FCB->PendingIrpList[FUNCTION_RECV_DATAGRAM] ); + ( &FCB->PendingIrpList[FUNCTION_RECV] ); NextIrp = CONTAINING_RECORD( ListEntry, IRP, Tail.Overlay.ListEntry ); NextIrpSp = IoGetCurrentIrpStackLocation( NextIrp ); RecvReq = NextIrpSp->Parameters.DeviceIoControl.Type3InputBuffer; @@ -396,6 +404,10 @@ AfdPacketSocketReadData(PDEVICE_OBJECT DeviceObject, PIRP Irp, if( !(RecvReq = LockRequest( Irp, IrpSp )) ) return UnlockAndMaybeComplete ( FCB, STATUS_NO_MEMORY, Irp, 0, NULL, FALSE ); + + RecvReq->BufferArray = LockBuffers( RecvReq->BufferArray, + RecvReq->BufferCount, + TRUE ); if( !IsListEmpty( &FCB->DatagramList ) ) { ListEntry = RemoveHeadList( &FCB->DatagramList ); @@ -420,9 +432,6 @@ AfdPacketSocketReadData(PDEVICE_OBJECT DeviceObject, PIRP Irp, ( FCB, Status, Irp, Irp->IoStatus.Information, NULL, TRUE ); } } else { - RecvReq->BufferArray = LockBuffers( RecvReq->BufferArray, - RecvReq->BufferCount, - TRUE ); - return LeaveIrpUntilLater( FCB, Irp, FUNCTION_RECV_DATAGRAM ); + return LeaveIrpUntilLater( FCB, Irp, FUNCTION_RECV ); } } diff --git a/reactos/drivers/net/afd/include/afd.h b/reactos/drivers/net/afd/include/afd.h index efd64c1f064..54246b65f20 100644 --- a/reactos/drivers/net/afd/include/afd.h +++ b/reactos/drivers/net/afd/include/afd.h @@ -1,4 +1,4 @@ -/* $Id: afd.h,v 1.21 2004/11/12 07:34:56 arty Exp $ +/* $Id: afd.h,v 1.22 2004/11/14 19:45:16 arty Exp $ * * COPYRIGHT: See COPYING in the top level directory * PROJECT: ReactOS kernel @@ -50,10 +50,9 @@ #define FUNCTION_CONNECT 0 #define FUNCTION_RECV 1 -#define FUNCTION_RECV_DATAGRAM 2 -#define FUNCTION_SEND 3 -#define FUNCTION_CLOSE 4 -#define MAX_FUNCTIONS 5 +#define FUNCTION_SEND 2 +#define FUNCTION_CLOSE 3 +#define MAX_FUNCTIONS 4 #define IN_FLIGHT_REQUESTS 3 diff --git a/reactos/drivers/net/tcpip/include/ports.h b/reactos/drivers/net/tcpip/include/ports.h new file mode 100644 index 00000000000..e71cc214a9a --- /dev/null +++ b/reactos/drivers/net/tcpip/include/ports.h @@ -0,0 +1,30 @@ +#ifndef _TCPIP_PORTS_H +#define _TCPIP_PORTS_H + +/* + * COPYRIGHT: See COPYING in the top level directory + * PROJECT: ReactOS TCP/IP protocol driver + * FILE: include/ports.h + * PURPOSE: Port allocation + * PROGRAMMERS: arty (ayerkes@speakeasy.net) + * REVISIONS: + * arty 20041114 Created + */ + +typedef struct _PORT_SET { + RTL_BITMAP ProtoBitmap; + PVOID ProtoBitBuffer; + UINT StartingPort; + UINT PortsToOversee; + FAST_MUTEX Mutex; +} PORT_SET, *PPORT_SET; + +VOID PortsStartup( PPORT_SET PortSet, + UINT StartingPort, + UINT PortsToManage ); +VOID PortsShutdown( PPORT_SET PortSet ); +VOID DeallocatePort( PPORT_SET PortSet, ULONG Port ); +BOOLEAN AllocatePort( PPORT_SET PortSet, ULONG Port ); +ULONG AllocateAnyPort( PPORT_SET PortSet ); + +#endif/*_TCPIP_PORTS_H*/ diff --git a/reactos/drivers/net/tcpip/include/precomp.h b/reactos/drivers/net/tcpip/include/precomp.h index 603d60baa14..b3032c3b6d1 100644 --- a/reactos/drivers/net/tcpip/include/precomp.h +++ b/reactos/drivers/net/tcpip/include/precomp.h @@ -7,6 +7,7 @@ #include #include #include +#include #include #include #include @@ -26,7 +27,6 @@ #include #include #include -#include #include #include #include @@ -34,3 +34,4 @@ #include #include #include +#include diff --git a/reactos/drivers/net/tcpip/include/tcpip.h b/reactos/drivers/net/tcpip/include/tcpip.h index e3e61ab2fc0..fbc74489cca 100644 --- a/reactos/drivers/net/tcpip/include/tcpip.h +++ b/reactos/drivers/net/tcpip/include/tcpip.h @@ -52,8 +52,6 @@ #include #include -#include - /* Macros */ @@ -156,7 +154,6 @@ extern KSPIN_LOCK EntityListLock; extern TDIEntityInfo *EntityList; extern ULONG EntityCount; extern ULONG EntityMax; -extern UDP_STATISTICS UDPStats; extern NTSTATUS TiGetProtocolNumber( PUNICODE_STRING FileName, PULONG Protocol ); diff --git a/reactos/drivers/net/tcpip/include/titypes.h b/reactos/drivers/net/tcpip/include/titypes.h index 585977faf5f..9fad10ec6a9 100644 --- a/reactos/drivers/net/tcpip/include/titypes.h +++ b/reactos/drivers/net/tcpip/include/titypes.h @@ -110,6 +110,8 @@ typedef VOID (*DATAGRAM_COMPLETION_ROUTINE)( NDIS_STATUS Status, ULONG Count); +typedef DATAGRAM_COMPLETION_ROUTINE PDATAGRAM_COMPLETION_ROUTINE; + typedef struct _DATAGRAM_RECEIVE_REQUEST { LIST_ENTRY ListEntry; /* Entry on list */ IP_ADDRESS RemoteAddress; /* Remote address we receive from (NULL means any) */ diff --git a/reactos/drivers/net/tcpip/include/udp.h b/reactos/drivers/net/tcpip/include/udp.h index 0af46b89e81..c06072b42df 100644 --- a/reactos/drivers/net/tcpip/include/udp.h +++ b/reactos/drivers/net/tcpip/include/udp.h @@ -7,6 +7,8 @@ #ifndef __UDP_H #define __UDP_H +#define UDP_STARTING_PORT 0x8000 +#define UDP_DYNAMIC_PORTS 0x8000 /* UDPv4 header structure */ typedef struct UDP_HEADER { @@ -34,6 +36,8 @@ typedef struct UDP_STATISTICS { ULONG NumAddresses; } UDP_STATISTICS, *PUDP_STATISTICS; +extern UDP_STATISTICS UDPStats; + VOID UDPSend( PVOID Context, PDATAGRAM_SEND_REQUEST SendRequest); @@ -52,7 +56,9 @@ NTSTATUS UDPReceiveDatagram( ULONG ReceiveLength, ULONG ReceiveFlags, PTDI_CONNECTION_INFORMATION ReturnInfo, - PULONG BytesReceived); + PULONG BytesReceived, + PDATAGRAM_COMPLETION_ROUTINE Complete, + PVOID Context); VOID UDPReceive( PNET_TABLE_ENTRY NTE, @@ -63,6 +69,8 @@ NTSTATUS UDPStartup( NTSTATUS UDPShutdown( VOID); +UINT UDPAllocatePort( UINT HintPort ); +VOID UDPFreePort( UINT Port ); #endif /* __UDP_H */ diff --git a/reactos/drivers/net/tcpip/tcpip/dispatch.c b/reactos/drivers/net/tcpip/tcpip/dispatch.c index 9b9821105e9..3c8bd9339ff 100644 --- a/reactos/drivers/net/tcpip/tcpip/dispatch.c +++ b/reactos/drivers/net/tcpip/tcpip/dispatch.c @@ -730,7 +730,9 @@ NTSTATUS DispTdiReceiveDatagram( DgramInfo->ReceiveLength, DgramInfo->ReceiveFlags, DgramInfo->ReturnDatagramInformation, - &BytesReceived); + &BytesReceived, + (PDATAGRAM_COMPLETION_ROUTINE)DispDataRequestComplete, + Irp); if (Status != STATUS_PENDING) { DispDataRequestComplete(Irp, Status, BytesReceived); diff --git a/reactos/drivers/net/tcpip/tcpip/fileobjs.c b/reactos/drivers/net/tcpip/tcpip/fileobjs.c index c2eb9bb031a..65ca49b3bc2 100644 --- a/reactos/drivers/net/tcpip/tcpip/fileobjs.c +++ b/reactos/drivers/net/tcpip/tcpip/fileobjs.c @@ -211,84 +211,6 @@ VOID DeleteConnectionEndpoint( TI_DbgPrint(MAX_TRACE, ("Leaving.\n")); } -#if 0 -VOID STDCALL RequestWorker(PVOID Context) -/* - * FUNCTION: Worker routine for processing address file object requests - * ARGUMENTS: - * Context = Pointer to context information (ADDRESS_FILE) - */ -{ - KIRQL OldIrql; - PLIST_ENTRY CurrentEntry; - PADDRESS_FILE AddrFile = Context; - - TI_DbgPrint(MID_TRACE, ("Called.\n")); - - TcpipAcquireSpinLock(&AddrFile->Lock, &OldIrql); - - /* Check it the address file should be deleted */ - if (AF_IS_PENDING(AddrFile, AFF_DELETE)) { - DATAGRAM_COMPLETION_ROUTINE RtnComplete; - PVOID RtnContext; - - RtnComplete = AddrFile->Complete; - RtnContext = AddrFile->Context; - - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - - DeleteAddress(AddrFile); - - (*RtnComplete)(RtnContext, TDI_SUCCESS, 0); - - TI_DbgPrint(MAX_TRACE, ("Leaving (delete).\n")); - - return; - } - - /* Check if there is a pending send request */ - if (AF_IS_PENDING(AddrFile, AFF_SEND)) { - if (!IsListEmpty(&AddrFile->TransmitQueue)) { - PDATAGRAM_SEND_REQUEST SendRequest; - - CurrentEntry = RemoveHeadList(&AddrFile->TransmitQueue); - SendRequest = CONTAINING_RECORD(CurrentEntry, DATAGRAM_SEND_REQUEST, ListEntry); - - AF_CLR_BUSY(AddrFile); - - ReferenceObject(AddrFile); - - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - - /* The send routine processes the send requests in - the transmit queue on the address file. When the - queue is empty the pending send flag is cleared. - The routine may return with the pending send flag - set. This can happen if there was not enough free - resources available to complete all send requests */ - DGSend(AddrFile, SendRequest); - - TcpipAcquireSpinLock(&AddrFile->Lock, &OldIrql); - DereferenceObject(AddrFile); - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - - TI_DbgPrint(MAX_TRACE, ("Leaving (send request).\n")); - - return; - } else - /* There was a pending send, but no send request. - Print a debug message and continue */ - TI_DbgPrint(MIN_TRACE, ("Pending send, but no send request.\n")); - } - - AF_CLR_BUSY(AddrFile); - - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - - TI_DbgPrint(MAX_TRACE, ("Leaving.\n")); -} -#endif - /* * FUNCTION: Open an address file object * ARGUMENTS: @@ -308,7 +230,7 @@ NTSTATUS FileOpenAddress( PADDRESS_FILE AddrFile; IPv4_RAW_ADDRESS IPv4Address; - TI_DbgPrint(MID_TRACE, ("Called.\n")); + TI_DbgPrint(MID_TRACE, ("Called (Proto %d).\n", Protocol)); AddrFile = ExAllocatePool(NonPagedPool, sizeof(ADDRESS_FILE)); if (!AddrFile) { @@ -329,9 +251,9 @@ NTSTATUS FileOpenAddress( /* FIXME: IPv4 only */ IPv4Address = Address->Address[0].Address[0].in_addr; if (IPv4Address == 0) - AddrFile->ADE = IPGetDefaultADE(ADE_UNICAST); + AddrFile->ADE = IPGetDefaultADE(ADE_UNICAST); else - AddrFile->ADE = AddrLocateADEv4(IPv4Address); + AddrFile->ADE = AddrLocateADEv4(IPv4Address); if (!AddrFile->ADE) { ExFreePool(AddrFile); @@ -339,8 +261,8 @@ NTSTATUS FileOpenAddress( return STATUS_INVALID_PARAMETER; } - TI_DbgPrint(MID_TRACE, ("Opening address %s for communication.\n", - A2S(&AddrFile->ADE->Address))); + TI_DbgPrint(MID_TRACE, ("Opening address %s for communication (P=%d U=%d).\n", + A2S(&AddrFile->ADE->Address), Protocol, IPPROTO_UDP)); /* Protocol specific handling */ switch (Protocol) { @@ -351,10 +273,12 @@ NTSTATUS FileOpenAddress( break; case IPPROTO_UDP: - /* FIXME: If specified port is 0, a port is chosen dynamically */ - AddrFile->Port = Address->Address[0].Address[0].sin_port; - AddrFile->Send = UDPSendDatagram; - break; + TI_DbgPrint(MID_TRACE,("Allocating udp port\n")); + AddrFile->Port = + UDPAllocatePort(Address->Address[0].Address[0].sin_port); + TI_DbgPrint(MID_TRACE,("Setting port %d\n", AddrFile->Port)); + AddrFile->Send = UDPSendDatagram; + break; default: /* Use raw IP for all other protocols */ @@ -376,9 +300,6 @@ NTSTATUS FileOpenAddress( InitializeListHead(&AddrFile->ReceiveQueue); InitializeListHead(&AddrFile->TransmitQueue); - /* Initialize work queue item. We use this for pending requests */ - /*ExInitializeWorkItem(&AddrFile->WorkItem, RequestWorker, AddrFile);*/ - /* Initialize spin lock that protects the address file object */ KeInitializeSpinLock(&AddrFile->Lock); @@ -420,40 +341,15 @@ NTSTATUS FileCloseAddress( TcpipAcquireSpinLock(&AddrFile->Lock, &OldIrql); - if (!AF_IS_BUSY(AddrFile)) { - /* Set address file object exclusive to us */ - AF_SET_BUSY(AddrFile); - AF_CLR_VALID(AddrFile); - - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - - DeleteAddress(AddrFile); - } else { - if (!AF_IS_PENDING(AddrFile, AFF_DELETE)) { - AddrFile->Complete = Request->RequestNotifyObject; - AddrFile->Context = Request->RequestContext; - - /* Shedule address file for deletion */ - AF_SET_PENDING(AddrFile, AFF_DELETE); - AF_CLR_VALID(AddrFile); - - if (!AF_IS_BUSY(AddrFile)) { - /* Worker function is not running, so shedule it to run */ - AF_SET_BUSY(AddrFile); - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - ExQueueWorkItem(&AddrFile->WorkItem, CriticalWorkQueue); - } else - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - - TI_DbgPrint(MAX_TRACE, ("Leaving (pending).\n")); - - return STATUS_PENDING; - } else - Status = STATUS_ADDRESS_CLOSED; - - TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); - } - + /* Set address file object exclusive to us */ + AF_SET_BUSY(AddrFile); + AF_CLR_VALID(AddrFile); + + TcpipReleaseSpinLock(&AddrFile->Lock, OldIrql); + UDPFreePort( AddrFile->Port ); + + DeleteAddress(AddrFile); + TI_DbgPrint(MAX_TRACE, ("Leaving.\n")); return Status;