xref: /haiku/src/add-ons/kernel/network/protocols/tcp/TCPEndpoint.h (revision 079eccf655ba39812b421ae1b87a727d41b50354)
1 /*
2  * Copyright 2006-2008, Haiku, Inc. All Rights Reserved.
3  * Distributed under the terms of the MIT License.
4  *
5  * Authors:
6  *		Andrew Galante, haiku.galante@gmail.com
7  *		Axel Dörfler, axeld@pinc-software.de
8  *		Hugo Santos, hugosantos@gmail.com
9  */
10 #ifndef TCP_ENDPOINT_H
11 #define TCP_ENDPOINT_H
12 
13 
14 #include "BufferQueue.h"
15 #include "EndpointManager.h"
16 #include "tcp.h"
17 
18 #include <ProtocolUtilities.h>
19 #include <net_protocol.h>
20 #include <net_stack.h>
21 #include <util/AutoLock.h>
22 #include <util/DoublyLinkedList.h>
23 #include <util/OpenHashTable.h>
24 
25 #include <stddef.h>
26 
27 
28 class WaitList {
29 public:
30 	WaitList(const char* name);
31 	~WaitList();
32 
33 	status_t InitCheck() const;
34 
35 	status_t Wait(MutexLocker& locker, bigtime_t timeout = B_INFINITE_TIMEOUT);
36 	void Signal();
37 
38 private:
39 	int32 fCondition;
40 	sem_id fSem;
41 };
42 
43 
44 class TCPEndpoint : public net_protocol, public ProtocolSocket {
45 public:
46 						TCPEndpoint(net_socket* socket);
47 						~TCPEndpoint();
48 
49 			status_t	InitCheck() const;
50 
51 			status_t	Open();
52 			status_t	Close();
53 			status_t	Free();
54 			status_t	Connect(const struct sockaddr* address);
55 			status_t	Accept(struct net_socket** _acceptedSocket);
56 			status_t	Bind(const sockaddr* address);
57 			status_t	Unbind(struct sockaddr* address);
58 			status_t	Listen(int count);
59 			status_t	Shutdown(int direction);
60 			status_t	SendData(net_buffer* buffer);
61 			ssize_t		SendAvailable();
62 			status_t	ReadData(size_t numBytes, uint32 flags,
63 							net_buffer** _buffer);
64 			ssize_t		ReadAvailable();
65 
66 			status_t	FillStat(struct net_stat* stat);
67 
68 			status_t	SetSendBufferSize(size_t length);
69 			status_t	SetReceiveBufferSize(size_t length);
70 
71 			status_t	GetOption(int option, void* value, int* _length);
72 			status_t	SetOption(int option, const void* value, int length);
73 
74 			tcp_state	State() const { return fState; }
75 			bool		IsBound() const;
76 			bool		IsLocal() const;
77 
78 			status_t	DelayedAcknowledge();
79 			status_t	SendAcknowledge(bool force);
80 
81 			int32		SegmentReceived(tcp_segment_header& segment,
82 							net_buffer* buffer);
83 
84 			void		Dump() const;
85 
86 private:
87 			void		_StartPersistTimer();
88 			void		_EnterTimeWait();
89 			void		_UpdateTimeWait();
90 			void		_Close();
91 			void		_CancelConnectionTimers();
92 			uint8		_CurrentFlags();
93 			bool		_ShouldSendSegment(tcp_segment_header& segment,
94 							uint32 length, uint32 segmentMaxSize,
95 							uint32 flightSize);
96 			status_t	_SendQueued(bool force = false);
97 			status_t	_SendQueued(bool force, uint32 sendWindow);
98 			int			_MaxSegmentSize(const struct sockaddr* address) const;
99 			status_t	_Disconnect(bool closing);
100 			ssize_t		_AvailableData() const;
101 			void		_NotifyReader();
102 			bool		_ShouldReceive() const;
103 			void		_HandleReset(status_t error);
104 			int32		_Spawn(TCPEndpoint* parent, tcp_segment_header& segment,
105 							net_buffer* buffer);
106 			int32		_ListenReceive(tcp_segment_header& segment,
107 							net_buffer* buffer);
108 			int32		_SynchronizeSentReceive(tcp_segment_header& segment,
109 							net_buffer* buffer);
110 			int32		_SegmentReceived(tcp_segment_header& segment,
111 							net_buffer* buffer);
112 			int32		_Receive(tcp_segment_header& segment,
113 							net_buffer* buffer);
114 			void		_UpdateTimestamps(tcp_segment_header& segment,
115 							size_t segmentLength);
116 			void		_MarkEstablished();
117 			status_t	_WaitForEstablished(MutexLocker& lock,
118 							bigtime_t timeout);
119 			bool		_AddData(tcp_segment_header& segment,
120 							net_buffer* buffer);
121 			void		_PrepareReceivePath(tcp_segment_header& segment);
122 			status_t	_PrepareSendPath(const sockaddr* peer);
123 			void		_Acknowledged(tcp_segment_header& segment);
124 			void		_Retransmit();
125 			void		_UpdateRoundTripTime(int32 roundTripTime);
126 			void		_ResetSlowStart();
127 			void		_DuplicateAcknowledge(tcp_segment_header& segment);
128 
129 	static	void		_TimeWaitTimer(net_timer* timer, void* _endpoint);
130 	static	void		_RetransmitTimer(net_timer* timer, void* _endpoint);
131 	static	void		_PersistTimer(net_timer* timer, void* _endpoint);
132 	static	void		_DelayedAcknowledgeTimer(net_timer* timer,
133 							void* _endpoint);
134 
135 private:
136 	HashTableLink<TCPEndpoint> fConnectionHashLink;
137 	HashTableLink<TCPEndpoint> fEndpointHashLink;
138 	friend class EndpointManager;
139 	friend class ConnectionHashDefinition;
140 	friend class EndpointHashDefinition;
141 
142 	mutex			fLock;
143 	EndpointManager* fManager;
144 	WaitList		fReceiveList;
145 	WaitList		fSendList;
146 	sem_id			fAcceptSemaphore;
147 	uint8			fOptions;
148 
149 	uint8			fSendWindowShift;
150 	uint8			fReceiveWindowShift;
151 
152 	tcp_sequence	fSendUnacknowledged;
153 	tcp_sequence	fSendNext;
154 	tcp_sequence	fSendMax;
155 	tcp_sequence	fSendUrgentOffset;
156 	uint32			fSendWindow;
157 	uint32			fSendMaxWindow;
158 	uint32			fSendMaxSegmentSize;
159 	BufferQueue		fSendQueue;
160 	tcp_sequence	fLastAcknowledgeSent;
161 	tcp_sequence	fInitialSendSequence;
162 	uint32			fDuplicateAcknowledgeCount;
163 
164 	net_route 		*fRoute;
165 		// TODO: don't use a net_route, but a net_route_info!!!
166 		// (the latter will automatically adapt to routing changes)
167 
168 	tcp_sequence	fReceiveNext;
169 	tcp_sequence	fReceiveMaxAdvertised;
170 	uint32			fReceiveWindow;
171 	uint32			fReceiveMaxSegmentSize;
172 	BufferQueue		fReceiveQueue;
173 	tcp_sequence	fInitialReceiveSequence;
174 
175 	// round trip time and retransmit timeout computation
176 	int32			fRoundTripTime;
177 	int32			fRoundTripDeviation;
178 	bigtime_t		fRetransmitTimeout;
179 
180 	uint32			fReceivedTimestamp;
181 
182 	uint32			fCongestionWindow;
183 	uint32			fSlowStartThreshold;
184 
185 	tcp_state		fState;
186 	uint32			fFlags;
187 
188 	// timer
189 	net_timer		fRetransmitTimer;
190 	net_timer		fPersistTimer;
191 	net_timer		fDelayedAcknowledgeTimer;
192 	net_timer		fTimeWaitTimer;
193 };
194 
195 #endif	// TCP_ENDPOINT_H
196