From 37e9151e7bc0b7341050286fde4341a8f0f9333c Mon Sep 17 00:00:00 2001 From: John Hodge Date: Wed, 3 Mar 2010 22:54:31 +0800 Subject: [PATCH] More work on TCP, approaching usable (untested) --- Kernel/Makefile.BuildNum | 2 +- Modules/IPStack/tcp.c | 68 +++++++++++++++++++++++++++++++++++----- Modules/IPStack/tcp.h | 23 ++++++++------ 3 files changed, 74 insertions(+), 19 deletions(-) diff --git a/Kernel/Makefile.BuildNum b/Kernel/Makefile.BuildNum index ef0be0a0..f7c128d5 100644 --- a/Kernel/Makefile.BuildNum +++ b/Kernel/Makefile.BuildNum @@ -1 +1 @@ -BUILD_NUM = 1464 +BUILD_NUM = 1465 diff --git a/Modules/IPStack/tcp.c b/Modules/IPStack/tcp.c index 9b3f8f45..326f044b 100644 --- a/Modules/IPStack/tcp.c +++ b/Modules/IPStack/tcp.c @@ -6,15 +6,15 @@ #include "ipv4.h" #include "tcp.h" -#define TCP_MIN_DYNPORT 0x1000 +#define TCP_MIN_DYNPORT 0xC000 #define TCP_MAX_HALFOPEN 1024 // Should be enough // === PROTOTYPES === void TCP_Initialise(); void TCP_StartConnection(tTCPConnection *Conn); -void TCP_SendPacket( tTCPConnection *Conn, size_t Length, tTCPHeader *Data ); +void TCP_SendPacket(tTCPConnection *Conn, size_t Length, tTCPHeader *Data); void TCP_GetPacket(tInterface *Interface, void *Address, int Length, void *Buffer); -void TCP_INT_HandleConnectionPacket(tTCPConnection *Connection, tTCPHeader *Header); +void TCP_INT_HandleConnectionPacket(tTCPConnection *Connection, tTCPHeader *Header, int Length); Uint16 TCP_GetUnusedPort(); int TCP_AllocatePort(Uint16 Port); int TCP_DeallocatePort(Uint16 Port); @@ -161,7 +161,7 @@ void TCP_GetPacket(tInterface *Interface, void *Address, int Length, void *Buffe continue; // We have a response! - TCP_INT_HandleConnectionPacket(conn, hdr); + TCP_INT_HandleConnectionPacket(conn, hdr, Length); return; } @@ -172,6 +172,8 @@ void TCP_GetPacket(tInterface *Interface, void *Address, int Length, void *Buffe continue; } + // TODO: Check for halfopen max + conn = calloc(1, sizeof(tTCPConnection)); conn->State = TCP_ST_HALFOPEN; conn->LocalPort = srv->Port; @@ -234,7 +236,7 @@ void TCP_GetPacket(tInterface *Interface, void *Address, int Length, void *Buffe if(conn->Interface->Type == 4 && !IP4_EQU(conn->RemoteIP.v4, *(tIPv4*)Address)) continue; - TCP_INT_HandleConnectionPacket(conn, hdr); + TCP_INT_HandleConnectionPacket(conn, hdr, Length); } } } @@ -242,9 +244,59 @@ void TCP_GetPacket(tInterface *Interface, void *Address, int Length, void *Buffe /** * \brief Handles a packet sent to a specific connection */ -void TCP_INT_HandleConnectionPacket(tTCPConnection *Connection, tTCPHeader *Header) -{ - +void TCP_INT_HandleConnectionPacket(tTCPConnection *Connection, tTCPHeader *Header, int Length) +{ + tTCPStoredPacket *pkt; + int dataLen; + + Connection->State = TCP_ST_OPEN; + if(Header->Flags & TCP_FLAG_SYN) { + Connection->NextSequenceRcv = Header->SequenceNumber + 1; + } + + if(Header->Flags & TCP_FLAG_ACK) { + // TODO: Process an ACKed Packet + Log("[TCP ] Conn %p, Packet 0x%x ACKed", Connection, Header->AcknowlegementNumber); + return ; + } + + // Allocate and fill cached packet + dataLen = Length - (Header->DataOffset&0xF)*4; + pkt = malloc( dataLen + sizeof(tTCPStoredPacket) ); + pkt->Next = NULL; + pkt->Sequence = Header->SequenceNumber; + memcpy(pkt->Data, (Uint8*)Header + (Header->DataOffset&0xF)*4, dataLen); + + if( Header->SequenceNumber != Connection->NextSequenceRcv ) + { + tTCPStoredPacket *tmp, *prev; + for(tmp = Connection->FuturePackets; + tmp; + prev = tmp, tmp = tmp->Next) + { + if(tmp->Sequence > pkt->Sequence) break; + } + if(prev) + prev->Next = pkt; + else + Connection->FuturePackets = pkt; + pkt->Next = tmp; + } + else + { + LOCK( &Connection->lRecievedPackets ); + if(Connection->RecievedPackets) + { + Connection->RecievedPacketsTail->Next = pkt; + Connection->RecievedPacketsTail = pkt; + } + else + { + Connection->RecievedPackets = pkt; + Connection->RecievedPacketsTail = pkt; + } + RELEASE( &Connection->lRecievedPackets ); + } } /** diff --git a/Modules/IPStack/tcp.h b/Modules/IPStack/tcp.h index fd04f7b7..87515ce9 100644 --- a/Modules/IPStack/tcp.h +++ b/Modules/IPStack/tcp.h @@ -9,6 +9,7 @@ typedef struct sTCPHeader tTCPHeader; typedef struct sTCPListener tTCPListener; +typedef struct sTCPStoredPacket tTCPStoredPacket; typedef struct sTCPConnection tTCPConnection; struct sTCPHeader @@ -71,6 +72,13 @@ struct sTCPListener tTCPConnection *volatile NewConnections; }; +struct sTCPStoredPacket +{ + struct sTCPStoredPacket *Next; + Uint32 Sequence; + Uint8 Data[]; +}; + struct sTCPConnection { struct sTCPConnection *Next; @@ -83,18 +91,13 @@ struct sTCPConnection int NextSequenceSend; //!< Next sequence value for outbound packets int NextSequenceRcv; //!< Next expected sequence value for inbound - int nQueuedPackets; //!< Number of packets not ACKed - struct { - int Sequence; - void *Data; - } *QueuedPackets; //!< Non-ACKed packets + tTCPStoredPacket *QueuedPackets; //!< Non-ACKed packets + tSpinlock lRecievedPackets; + tTCPStoredPacket *RecievedPackets; //!< Unread Packets + tTCPStoredPacket *RecievedPacketsTail; //!< Unread Packets (End of list) - int nFuturePackets; //!< Number of packets recieved that are out of sequence - struct { - int SequenceNum; - void *Data; - } **FuturePackets; //!< Out of sequence packets + tTCPStoredPacket *FuturePackets; //!< Out of sequence packets union { tIPv4 v4; -- 2.20.1