3 Copyright (c) 2005 - 2006, Intel Corporation
\r
4 All rights reserved. This program and the accompanying materials
\r
5 are licensed and made available under the terms and conditions of the BSD License
\r
6 which accompanies this distribution. The full text of the license may be found at
\r
7 http://opensource.org/licenses/bsd-license.php
\r
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
\r
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
\r
26 #include <Protocol/IP4.h>
\r
27 #include <Protocol/Tcp4.h>
\r
28 #include <Protocol/Udp4.h>
\r
30 #include <Library/NetLib.h>
\r
31 #include <Library/DebugLib.h>
\r
32 #include <Library/UefiRuntimeServicesTableLib.h>
\r
33 #include <Library/UefiDriverEntryPoint.h>
\r
34 #include <Library/UefiBootServicesTableLib.h>
\r
35 #include <Library/BaseLib.h>
\r
36 #include <Library/UefiLib.h>
\r
37 #include <Library/MemoryAllocationLib.h>
\r
38 #include <Library/BaseMemoryLib.h>
\r
40 #define SOCK_SND_BUF 0
\r
41 #define SOCK_RCV_BUF 1
\r
43 #define SOCK_BUFF_LOW_WATER 2 * 1024
\r
44 #define SOCK_RCV_BUFF_SIZE 8 * 1024
\r
45 #define SOCK_SND_BUFF_SIZE 8 * 1024
\r
46 #define SOCK_BACKLOG 5
\r
48 #define PROTO_RESERVED_LEN 20
\r
50 #define SO_NO_MORE_DATA 0x0001
\r
55 // When a socket is created it enters into SO_UNCONFIGURED,
\r
56 // no actions can be taken on this socket, only after calling
\r
57 // SockConfigure. The state transition diagram of socket is
\r
60 // SO_UNCONFIGURED --- SO_CONFIGURED --- SO_CONNECTING
\r
62 // | ---> SO_LISTENING |
\r
64 // |------------------SO_DISCONNECTING<-- SO_CONNECTED
\r
66 // A passive socket can only go into SO_LISTENING and
\r
67 // SO_UNCONFIGURED state. SO_XXXING state is a middle state
\r
68 // when a socket is undergoing a protocol procedure such
\r
69 // as requesting a TCP connection.
\r
82 SO_UNCONFIGURED = 0,
\r
83 SO_CONFIGURED_ACTIVE,
\r
84 SO_CONFIGURED_PASSIVE,
\r
86 } SOCK_CONFIGURE_STATE;
\r
88 #define SOCK_NO_MORE_DATA(Sock) ((Sock)->Flag |= SO_NO_MORE_DATA)
\r
90 #define SOCK_IS_UNCONFIGURED(Sock) ((Sock)->ConfigureState == SO_UNCONFIGURED)
\r
92 #define SOCK_IS_CONFIGURED(Sock) \
\r
93 (((Sock)->ConfigureState == SO_CONFIGURED_ACTIVE) || \
\r
94 ((Sock)->ConfigureState == SO_CONFIGURED_PASSIVE))
\r
96 #define SOCK_IS_CONFIGURED_ACTIVE(Sock) \
\r
97 ((Sock)->ConfigureState == SO_CONFIGURED_ACTIVE)
\r
99 #define SOCK_IS_CONNECTED_PASSIVE(Sock) \
\r
100 ((Sock)->ConfigureState == SO_CONFIGURED_PASSIVE)
\r
102 #define SOCK_IS_NO_MAPPING(Sock) \
\r
103 ((Sock)->ConfigureState == SO_NO_MAPPING)
\r
105 #define SOCK_IS_CLOSED(Sock) ((Sock)->State == SO_CLOSED)
\r
107 #define SOCK_IS_LISTENING(Sock) ((Sock)->State == SO_LISTENING)
\r
109 #define SOCK_IS_CONNECTING(Sock) ((Sock)->State == SO_CONNECTING)
\r
111 #define SOCK_IS_CONNECTED(Sock) ((Sock)->State == SO_CONNECTED)
\r
113 #define SOCK_IS_DISCONNECTING(Sock) ((Sock)->State == SO_DISCONNECTING)
\r
115 #define SOCK_IS_NO_MORE_DATA(Sock) (0 != ((Sock)->Flag & SO_NO_MORE_DATA))
\r
117 #define SOCK_SIGNATURE EFI_SIGNATURE_32 ('S', 'O', 'C', 'K')
\r
119 #define SOCK_FROM_THIS(a) CR ((a), SOCKET, NetProtocol, SOCK_SIGNATURE)
\r
121 #define SET_RCV_BUFFSIZE(Sock, Size) ((Sock)->RcvBuffer.HighWater = (Size))
\r
123 #define GET_RCV_BUFFSIZE(Sock) ((Sock)->RcvBuffer.HighWater)
\r
125 #define GET_RCV_DATASIZE(Sock) (((Sock)->RcvBuffer.DataQueue)->BufSize)
\r
127 #define SET_SND_BUFFSIZE(Sock, Size) ((Sock)->SndBuffer.HighWater = (Size))
\r
129 #define GET_SND_BUFFSIZE(Sock) ((Sock)->SndBuffer.HighWater)
\r
131 #define GET_SND_DATASIZE(Sock) (((Sock)->SndBuffer.DataQueue)->BufSize)
\r
133 #define SET_BACKLOG(Sock, Value) ((Sock)->BackLog = (Value))
\r
135 #define GET_BACKLOG(Sock) ((Sock)->BackLog)
\r
137 #define SOCK_ERROR(Sock, Error) ((Sock)->SockError = (Error))
\r
139 #define SND_BUF_HDR_LEN(Sock) \
\r
140 ((SockBufFirst (&((Sock)->SndBuffer)))->TotalSize)
\r
142 #define RCV_BUF_HDR_LEN(Sock) \
\r
143 ((SockBufFirst (&((Sock)->RcvBuffer)))->TotalSize)
\r
145 #define SOCK_FROM_TOKEN(Token) (((SOCK_TOKEN *) (Token))->Sock)
\r
147 #define PROTO_TOKEN_FORM_SOCK(SockToken, Type) \
\r
148 ((Type *) (((SOCK_TOKEN *) (SockToken))->Token))
\r
150 typedef struct _SOCKET SOCKET;
\r
152 typedef struct _SOCK_COMPLETION_TOKEN {
\r
155 } SOCK_COMPLETION_TOKEN;
\r
157 typedef struct _SOCK_IO_TOKEN {
\r
158 SOCK_COMPLETION_TOKEN Token;
\r
166 // the request issued from socket layer to protocol layer
\r
169 SOCK_ATTACH, // attach current socket to a new PCB
\r
170 SOCK_DETACH, // detach current socket from the PCB
\r
171 SOCK_CONFIGURE, // configure attached PCB
\r
172 SOCK_FLUSH, // flush attached PCB
\r
173 SOCK_SND, // need protocol to send something
\r
174 SOCK_SNDPUSH, // need protocol to send pushed data
\r
175 SOCK_SNDURG, // need protocol to send urgent data
\r
176 SOCK_CONSUMED, // application has retrieved data from socket
\r
177 SOCK_CONNECT, // need to connect to a peer
\r
178 SOCK_CLOSE, // need to close the protocol process
\r
179 SOCK_ABORT, // need to reset the protocol process
\r
180 SOCK_POLL, // need to poll to the protocol layer
\r
181 SOCK_ROUTE, // need to add a route information
\r
182 SOCK_MODE, // need to get the mode data of the protocol
\r
183 SOCK_GROUP // need to join a mcast group
\r
190 SOCK_DGRAM, // this socket providing datagram service
\r
191 SOCK_STREAM // this socket providing stream service
\r
195 // the handler of protocol for request from socket
\r
199 (*SOCK_PROTO_HANDLER) (
\r
200 IN SOCKET * Socket, // the socket issuing the request to protocol
\r
201 IN SOCK_REQUEST Request, // the request issued by socket
\r
202 IN VOID *RequestData // the request related data
\r
206 // the buffer structure of rcvd data and send data used by socket
\r
208 typedef struct _SOCK_BUFFER {
\r
209 UINT32 HighWater; // the buffersize upper limit of sock_buffer
\r
210 UINT32 LowWater; // the low warter mark of sock_buffer
\r
211 NET_BUF_QUEUE *DataQueue; // the queue to buffer data
\r
216 // socket provided oprerations for low layer protocol
\r
220 // socket provided operations for user interface
\r
225 IN SOCK_STATE State
\r
229 // when the connection establishment process for a Sock
\r
230 // is finished low layer protocol calling this function
\r
231 // to notify socket layer
\r
234 SockConnEstablished (
\r
244 // called by low layer protocol to trim send buffer of
\r
245 // Sock, when Count data is sent out completely
\r
254 // called by low layer protocol to get Len of data from
\r
255 // socket to send and copy it in Dest
\r
258 SockGetDataToSend (
\r
266 // called by low layer protocol to notify socket no more data can be
\r
275 // called by low layer protocol to append a NetBuffer
\r
276 // to rcv buffer of sock
\r
281 IN NET_BUF *NetBuffer,
\r
299 IN EFI_STATUS Error
\r
304 (*SOCK_CREATE_CALLBACK) (
\r
311 (*SOCK_DESTROY_CALLBACK) (
\r
317 // the initialize data for create a new socket
\r
319 typedef struct _SOCK_INIT_DATA {
\r
323 SOCKET *Parent; // the parent of this socket
\r
324 UINT32 BackLog; // the connection limit for listening socket
\r
325 UINT32 SndBufferSize; // the high warter mark of send buffer
\r
326 UINT32 RcvBufferSize; // the high warter mark of receive buffer
\r
327 VOID *Protocol; // the pointer to protocol function template
\r
328 // wanted to install on socket
\r
331 // Callbacks after socket is created and before socket is to be destroyed.
\r
333 SOCK_CREATE_CALLBACK CreateCallback;
\r
334 SOCK_DESTROY_CALLBACK DestroyCallback;
\r
338 // Opaque protocol data.
\r
343 SOCK_PROTO_HANDLER ProtoHandler;
\r
345 EFI_HANDLE DriverBinding; // the driver binding handle
\r
348 // the socket structure representing a network service access point
\r
353 // socket description information
\r
356 EFI_HANDLE SockHandle; // the virtual handle of the socket
\r
357 EFI_HANDLE DriverBinding; // socket't driver binding protocol
\r
358 EFI_DEVICE_PATH_PROTOCOL *ParentDevicePath;
\r
359 EFI_DEVICE_PATH_PROTOCOL *DevicePath;
\r
360 NET_LIST_ENTRY Link;
\r
361 SOCK_CONFIGURE_STATE ConfigureState;
\r
365 NET_LOCK Lock; // the lock of socket
\r
366 SOCK_BUFFER SndBuffer; // send buffer of application's data
\r
367 SOCK_BUFFER RcvBuffer; // receive buffer of received data
\r
368 EFI_STATUS SockError; // the error returned by low layer protocol
\r
369 BOOLEAN IsDestroyed;
\r
372 // fields used to manage the connection request
\r
374 UINT32 BackLog; // the limit of connection to this socket
\r
375 UINT32 ConnCnt; // the current count of connections to it
\r
376 SOCKET *Parent; // listening parent that accept the connection
\r
377 NET_LIST_ENTRY ConnectionList; // the connections maintained by this socket
\r
379 // the queue to buffer application's asynchronous token
\r
381 NET_LIST_ENTRY ListenTokenList;
\r
382 NET_LIST_ENTRY RcvTokenList;
\r
383 NET_LIST_ENTRY SndTokenList;
\r
384 NET_LIST_ENTRY ProcessingSndTokenList;
\r
386 SOCK_COMPLETION_TOKEN *ConnectionToken; // app's token to signal if connected
\r
387 SOCK_COMPLETION_TOKEN *CloseToken; // app's token to signal if closed
\r
390 // interface for low level protocol
\r
392 SOCK_PROTO_HANDLER ProtoHandler; // the request handler of protocol
\r
393 UINT8 ProtoReserved[PROTO_RESERVED_LEN]; // Data fields reserved for protocol
\r
395 EFI_TCP4_PROTOCOL TcpProtocol;
\r
396 EFI_UDP4_PROTOCOL UdpProtocol;
\r
402 SOCK_CREATE_CALLBACK CreateCallback;
\r
403 SOCK_DESTROY_CALLBACK DestroyCallback;
\r
408 // the token structure buffered in socket layer
\r
410 typedef struct _SOCK_TOKEN {
\r
411 NET_LIST_ENTRY TokenList; // the entry to add in the token list
\r
412 SOCK_COMPLETION_TOKEN *Token; // The application's token
\r
413 UINT32 RemainDataLen; // unprocessed data length
\r
414 SOCKET *Sock; // the poninter to the socket this token
\r
419 // reserved data to access the NET_BUF delivered by UDP driver
\r
421 typedef struct _UDP_RSV_DATA {
\r
422 EFI_TIME TimeStamp;
\r
423 EFI_UDP4_SESSION_DATA Session;
\r
427 // reserved data to access the NET_BUF delivered by TCP driver
\r
429 typedef struct _TCP_RSV_DATA {
\r
434 // call it to creat a socket and attach it to a PCB
\r
438 IN SOCK_INIT_DATA *SockInitData
\r
442 // call it to destroy a socket and its related PCB
\r
450 // call it to configure a socket and its related PCB
\r
455 IN VOID *ConfigData
\r
459 // call it to connect a socket to the peer
\r
468 // call it to issue an asynchronous listen token to the socket
\r
477 // Call it to send data using this socket
\r
486 // Call it to receive data from this socket
\r
495 // Call it to flush a socket
\r
503 // Call it to close a socket in the light of policy in Token
\r
513 // Call it to get the mode data of low layer protocol
\r
522 // call it to add this socket instance into a group
\r
531 // call it to add a route entry for this socket instance
\r
540 // Supporting function to operate on socket buffer
\r
544 IN SOCK_BUFFER *Sockbuf
\r
549 IN SOCK_BUFFER *Sockbuf,
\r
550 IN NET_BUF *SockEntry
\r