PERFORCE change 120673 for review

Alexey Tarasov taleks at FreeBSD.org
Thu May 31 16:09:02 UTC 2007


http://perforce.freebsd.org/chv.cgi?CH=120673

Change 120673 by taleks at taleks_th on 2007/05/31 16:08:23

	Started adding of UDP, sockets and DNS resolving. Most of functions are stubs. Added pxe_filter module to make filtration of incoming packets and serves as ip/port data storage for sockets. pxe_udp module  - handles UDP protocol. pxe_dns - DNS resolving module. Updated pxe_arp with  stats getting function. pxe_sock module now has only send/recv buffer related information, all ip/port data went to pxe_filter.

Affected files ...

.. //depot/projects/soc2007/taleks-pxe_http/Makefile#4 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_arp.c#5 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_arp.h#5 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_core.c#11 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_core.h#9 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_dns.c#1 add
.. //depot/projects/soc2007/taleks-pxe_http/pxe_dns.h#1 add
.. //depot/projects/soc2007/taleks-pxe_http/pxe_filter.c#1 add
.. //depot/projects/soc2007/taleks-pxe_http/pxe_filter.h#1 add
.. //depot/projects/soc2007/taleks-pxe_http/pxe_icmp.c#7 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_icmp.h#6 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_sock.c#4 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_sock.h#4 edit
.. //depot/projects/soc2007/taleks-pxe_http/pxe_udp.c#1 add
.. //depot/projects/soc2007/taleks-pxe_http/pxe_udp.h#1 add

Differences ...

==== //depot/projects/soc2007/taleks-pxe_http/Makefile#4 (text+ko) ====

@@ -4,7 +4,7 @@
 INTERNALLIB=
 
 SRCS= pxe_conv.c pxe_core.h pxe_isr.S pxe_sock.c pxe_arp.c  pxe_ip.c pxe_mutex.c \
-	pxe_core.c pxe_icmp.c pxe_mem.c
+	pxe_core.c pxe_icmp.c pxe_mem.c pxe_udp.c pxe_filter.c pxe_dns.c
 
 CFLAGS+=	-I${.CURDIR}/../../common -I${.CURDIR}/../btx/lib \
 		-I${.CURDIR}/../../../contrib/dev/acpica \
@@ -13,7 +13,7 @@
 CFLAGS+=	-I${.CURDIR}/../../../../lib/libstand/
 
 #debug flag
-#CFLAGS+=	-DPXE_DEBUG
+CFLAGS+=	-DPXE_DEBUG
 #CFLAGS+=	-DPXE_DEBUG_HELL
 
 .include <bsd.lib.mk>

==== //depot/projects/soc2007/taleks-pxe_http/pxe_arp.c#5 (text+ko) ====

@@ -73,6 +73,31 @@
 	return (NULL);
 }
 
+void
+pxe_arp_stats()
+{
+	int entry = 0;
+	int limit = (arp_usage > MAX_ARP_ENTRIES) ? MAX_ARP_ENTRIES : arp_usage;
+
+	printf("ARP updates: %d\n", arp_usage);
+
+	for (; entry < limit; ++entry) {
+		
+		PXE_IPADDR	ip;
+		uint8_t		*mac =  arp_table[entry].mac;
+		ip.ip = arp_table[entry].ip4.ip;
+		
+		if ( (ip.ip == 0) || (mac == NULL) )
+			continue;
+
+		printf("%d.%d.%d.%d\t%2x:%2x:%2x:%2x:%2x:%2x\n",
+			ip.octet[0], ip.octet[1], ip.octet[2], ip.octet[3],
+			mac[0],  mac[1], mac[2], mac[3], mac[4], mac[5]
+		);
+	}
+
+}
+
 /*
  *  pxe_arp_protocol() - process received arp packet, this function is called in style
  *                     of pxe_protocol_call function type, but last two parameters are unused

==== //depot/projects/soc2007/taleks-pxe_http/pxe_arp.h#5 (text+ko) ====

@@ -33,9 +33,11 @@
 /* initialisation routine */
 void pxe_arp_init();
 /* find MAC by provided ip */
-const MAC_ADDR* pxe_arp_ip4mac(uint32_t ip);
+const MAC_ADDR *pxe_arp_ip4mac(uint32_t ip);
 /* protocol handler for received packets */
 int pxe_arp_protocol(PXE_PACKET *pack, uint8_t function, void *data);
+/* ARP table statistics */
+void pxe_arp_stats();
 
 /* ARP packet types */
 #define PXE_ARPOP_REQUEST	1

==== //depot/projects/soc2007/taleks-pxe_http/pxe_core.c#11 (text+ko) ====

@@ -11,6 +11,7 @@
 #include "pxe_isr.h"
 #include "pxe_mem.h"
 #include "pxe_mutex.h"
+#include "pxe_udp.h"
 
 /* PXE API calls here will be made in same way as in pxeboot.
  * the only difference - installation of isr, that was not needed in pxe.c.
@@ -25,7 +26,10 @@
 static pxe_t	    *pxe   = NULL;    /* !PXE */
 static BOOTPLAYER   bootplayer;         /* PXE Cached information. */
 
-
+/* TODO: to think if packets queue must be in pxe_core.
+ *    It seems, it'll be used  only  by TCP 
+ */
+ 
 /* pxe core structures*/
 PXE_PACKET          core_packets[PXE_MAX_PACKETS];  /* buffered packets */
 pxe_protocol_call   core_protocol[256];    /* protocol's  callback fuctions */
@@ -34,6 +38,7 @@
 /* NIC info */
 PXE_IPADDR          nic_ip = {0};
 MAC_ADDR	    nic_mac;	/* may be init it also by zero? */
+PXE_IPADDR          ns_ip = {0};/* nameserver addr */
 
 /* core packet statistics */
 uint32_t   	    packets_dropped = 0;
@@ -305,11 +310,18 @@
 	printf("my ip: %d.%d.%d.%d\n", nic_ip.octet[0], nic_ip.octet[1], nic_ip.octet[2], nic_ip.octet[3]);
 						/* my MAC */
 	pxe_memcpy(&bootplayer.CAddr, &nic_mac, MAC_ADDR_LEN);
-	printf("my MAC: %2.2x:%2.2x:%2.2x:%2.2x:%2.2x:%2.2x\n", nic_mac[0], nic_mac[1], nic_mac[2], nic_mac[3], nic_mac[4], nic_mac[5]);
+	printf("my MAC: %2.2x:%2.2x:%2.2x:%2.2x:%2.2x:%2.2x\n",
+	    nic_mac[0], nic_mac[1], nic_mac[2], nic_mac[3], nic_mac[4], nic_mac[5]);
 
+	ns_ip.ip = 0x0100a8c0;		/* TODO: to determiny nameserver ip*/
+	
 	pxe_arp_init();
+	pxe_filter_init();
+	pxe_socket_init();
 	pxe_icmp_init();
+	pxe_udp_init();
 	
+	
 	pxe_ip_route_init(0x0100a8c0);	/* NOTE: setting default route 192.168.0.1
 					 * need to determiny gateway by getting info drom DHCP packets,
 					 * but cached packets for some resons have no gip set. So,
@@ -349,11 +361,9 @@
 	 
 #ifdef PXE_DEBUG
 	printf("pxe_core_install_isr() info:\n");
-	printf("IRQ (int): %d (%d)\n", undi_info->IntNumber, int_num);
-	printf("Base io: %d\n", undi_info->BaseIo);
-	printf("MTU: %d\n", undi_info->MaxTranUnit);
-	printf("RX buffer queue: %d\n", undi_info->RxBufCt);
-	printf("TX buffer queue: %d\n", undi_info->TxBufCt);
+	printf("\tIRQ (int): %d (%d)\n", undi_info->IntNumber, int_num);
+	printf("\tMTU: %d\n", undi_info->MaxTranUnit);
+	printf("\tRX/TX buffer queue: %d/%d\n", undi_info->RxBufCt, undi_info->TxBufCt);
 #endif
 	__pxe_entry_seg2 = pxe->EntryPointSP.segment;
 	__pxe_entry_off2 = pxe->EntryPointSP.offset;
@@ -368,7 +378,7 @@
 	v86int();
 	v86.ctl  = V86_FLAGS;
 	
-	printf("chained handler @ 0x%x:0x%x (0x%x/0x%x:0x%x)\n", v86.ebx, v86.edx, v86.ecx, VTOPSEG(__chained_irq_off), VTOPOFF(__chained_irq_off));
+	printf("\tchained handler @ 0x%x:0x%x\n", v86.ebx, v86.edx);
 
 /*	v86.ctl  = V86_ADDR | V86_CALLF | V86_FLAGS;
  	v86.addr = (VTOPSEG(__mask_irq) << 16) | VTOPOFF(__mask_irq);
@@ -788,7 +798,7 @@
 
 		if (protocol == PXE_PROTOCOL_ARP) {
 	
-			pxe_arp_protocol(&dummy_pack, PXE_CORE_FRAG, NULL);
+			pxe_arp_protocol(&dummy_pack, PXE_CORE_HANDLE, NULL);
 			++processed_packets;
 
 			/* aasume ARP packet always in one fragment */
@@ -802,7 +812,7 @@
 
 		if  ( (!core_protocol[iphdr->protocol]) ||
 		      (!core_protocol[iphdr->protocol](&dummy_pack,
-				PXE_CORE_FRAG, NULL)) ) {
+				(buffer_size == frame_size) ? PXE_CORE_HANDLE : PXE_CORE_FRAG, NULL)) ) {
 
 			drop_flag = 1;
 		} else {
@@ -1012,6 +1022,13 @@
 	return nic_ip.ip;
 }
 
+uint32_t
+pxe_get_nsip32()
+{
+
+	return ns_ip.ip;
+}
+
 const MAC_ADDR*
 pxe_get_mymac()
 {

==== //depot/projects/soc2007/taleks-pxe_http/pxe_core.h#9 (text+ko) ====

@@ -116,4 +116,7 @@
 /* returns NIC MAC */
 const MAC_ADDR *pxe_get_mymac();
 
+/* returns nameserver ip */
+uint32_t pxe_get_nsip32();
+
 #endif // PXE_CORE_H_INCLUDED

==== //depot/projects/soc2007/taleks-pxe_http/pxe_icmp.c#7 (text+ko) ====

@@ -112,7 +112,7 @@
 	reply_icmphdr->checksum =
 	        ~pxe_ip_checksum(reply_icmphdr, sizeof(PXE_ICMP_HDR) + data_size);
 		
-	if (!pxe_ip_send(pack->data, iphdr->src_ip, 0x01, pack->data_size, 1) && echo_flags) {
+	if (!pxe_ip_send(pack->data, iphdr->src_ip, PXE_ICMP_PROTOCOL, pack->data_size, 1) && echo_flags) {
 		printf("pxe_ping(): failed to send echo reply.\n");
 	}
 
@@ -127,8 +127,7 @@
 {
 
 	/* register protocol in pxe_core protocols table. */
-	/* 0x01 - ICMP protocol */
-	pxe_core_register(0x01, pxe_icmp_callback);
+	pxe_core_register(PXE_ICMP_PROTOCOL, pxe_icmp_callback);
 
 	return (1);
 }
@@ -174,7 +173,7 @@
 		icmphdr->checksum =
 		    ~(pxe_ip_checksum(icmphdr, sizeof(PXE_ICMP_HDR) + 32));
 
-	    	if (!pxe_ip_send(data, ip->ip, 0x01, pack_size, 1) && echo_flags) {
+	    	if (!pxe_ip_send(data, ip->ip, PXE_ICMP_PROTOCOL, pack_size, 1) && echo_flags) {
 			printf("pxe_ping(): failed to send echo reply.\n");
 		}	
 

==== //depot/projects/soc2007/taleks-pxe_http/pxe_icmp.h#6 (text+ko) ====

@@ -9,6 +9,7 @@
  * reference: RFC792
  */
 
+#define PXE_ICMP_PROTOCOL	0x01
 /* ICMP header */
 typedef struct pxe_icmp_hdr {
     uint8_t	type;		/* type of ICMP  packet */
@@ -20,14 +21,16 @@
 
 /* timeout in milliseconds */
 #define PXE_ICMP_TIMEOUT	5000
+
 /* pxe_ping - send icmp echo request packets to host
  *    in:
  *       ip      - host ip address
  *       count   - packets to send, 0 - to send infinte count
+ *	 flags	 - 1 echo ping information to screen
  *   out:
  *       successfull recieved echo's count
  */
-int pxe_ping(PXE_IPADDR *ip, int count);
+int pxe_ping(PXE_IPADDR *ip, int count, int flags);
 
 /* pxe_icmp_init - inits icmp protocol
  *    in:

==== //depot/projects/soc2007/taleks-pxe_http/pxe_sock.c#4 (text+ko) ====

@@ -1,81 +1,377 @@
 #include "pxe_mem.h"
+#include "pxe_filter.h"
 #include "pxe_sock.h"
-#include "pxe_tcp.h"
+#include "pxe_udp.h"
 
+static PXE_SOCKET	pxe_sockets[PXE_DEFAULT_SOCKETS];
+static uint16_t		avail_port = 1025;
 
-PXE_SOCKET pxe_sockets[PXE_DEFAULT_SOCKETS];
-
-int
-pxe_sockets_init()
+void
+pxe_socket_init()
 {
 
 	pxe_memset(pxe_sockets, 0, sizeof(pxe_sockets));
-
-	return (1);
 }
 
 
 int
-pxe_tcp_socket()
+pxe_socket_alloc()
 {
 	int sock_index = 0;
 
 	/* searching free sockets */
 	for (; sock_index < PXE_DEFAULT_SOCKETS; ++sock_index) {
 
-		if (pxe_sockets[sock_index].state == PXE_TCP_CLOSED) {
+		if (pxe_sockets[sock_index].state == PXE_SOCKET_FREE) {
 			/* found free socket */
-			pxe_sockets[sock_index].state = PXE_TCP_MARK;
+			pxe_memset(&pxe_sockets[sock_index], 0, sizeof(PXE_SOCKET));
+			pxe_sockets[sock_index].state = PXE_SOCKET_USED;
 			return sock_index;
 		}
 	}
 
 	return (-1); /* no socket found :( */
 }
-/*
+
+int
+pxe_socket_free(int socket)
+{
+	PXE_SOCKET *sock = &pxe_sockets[socket];
+
+	sock->state = PXE_SOCKET_FREE;
+	
+	if (sock->filter) {
+		pxe_filter_remove(sock->filter);
+		sock->filter = NULL;
+	}
+	
+	return (1);
+}
+
+
+int
+pxe_socket()
+{
+	int socket = pxe_socket_alloc();
+
+	/* allocating structure */
+	if (socket == -1)
+		return (-1);
+
+	/* creating buffers */
+	PXE_SOCKET	*sock = &pxe_sockets[socket];
+	
+	sock->send_buffer.data = pxe_alloc(PXE_DEFAULT_SEND_BUFSIZE);
+	
+	if (sock->send_buffer.data == NULL) {
+	
+		pxe_socket_free(socket);
+		return (-1);
+	}
+	
+	sock->send_buffer.bufsize = PXE_DEFAULT_SEND_BUFSIZE;
+	sock->send_buffer.bufleft = PXE_DEFAULT_SEND_BUFSIZE;
+	sock->send_buffer.next_data = sock->send_buffer.data;
+
+	sock->recv_buffer.data = pxe_alloc(PXE_DEFAULT_RECV_BUFSIZE);
+	
+	if (sock->recv_buffer.data == NULL) {
+	
+		pxe_free(sock->send_buffer.data);
+		pxe_socket_free(socket);
+		return (-1);
+	}
+	
+	sock->recv_buffer.bufsize = PXE_DEFAULT_RECV_BUFSIZE;
+	sock->recv_buffer.bufleft = PXE_DEFAULT_RECV_BUFSIZE;	
+	sock->recv_buffer.next_data = sock->recv_buffer.data;
+	
+	return (socket);		
+}
+
 int
-pxe_connect(int socket, uint32_t ip, uint16_t port)
+pxe_close(int socket)
 {
-	int result = pxe_tcp_send_packet(pxe_sockets[socket], NULL, 0,
-	                 PXE_TCP_SYN);
 
-	if (result == 0) {
+	if (socket > PXE_DEFAULT_SOCKETS) {
 		return (0);
 	}
+	
+	PXE_SOCKET	*sock = &pxe_sockets[socket];
+	
+	pxe_free(sock->send_buffer.data);
+	pxe_free(sock->recv_buffer.data);
+	
+	return pxe_socket_free(socket);
+}
 
-	pxe_sockets[socket].state = PXE_TCP_SYN_SENT;
-	return (1);
+int
+pxe_listen(int socket, uint8_t proto, uint16_t port) 
+{
+#ifdef PXE_DEBUG
+	printf("pxe_listen(): proto 0x%x, port: %d.\n", proto, port);
+#endif
 
-	pxe_tcp_recv_packet(pxe_sockets[socket], NULL, 0,
-	    PXE_TCP_SYN | PXE_TCP_ACK);
-	pxe_tcp_send_packet(pxe_sockets[socket], NULL, 0, PXE_TCP_ACK);
+	PXE_FILTER_ENTRY *filter = pxe_filter_add(0, 0, pxe_get_myip32(), port, &pxe_sockets[socket], proto);
+	
+	if (filter == NULL) {
+		printf("pxe_listen(): failed to add filter.\n");
+		return (-1);
+	}
+	
+	pxe_filter_mask(filter, 0, 0, 0xffffffff, 0xffff);
+	
+	pxe_sockets[socket].filter = filter;
+	
+	if (proto == PXE_UDP_PROTOCOL) {	/* for UDP it's fake listen */
+		return (socket);
+	}
+	
+	while (pxe_sockets[socket].waiting == 0) {
+#ifdef PXE_DEBUG
+		twiddle();
+#endif		
+		if (!pxe_core_recv_packets()) {
+			delay(100000);
+		}
+	}
+	
+	return (0);
 }
 
 int
-pxe_send(int socket, void *buf, size_t buflen)
+pxe_accept(int socket)
+{
+
+	if (socket > PXE_DEFAULT_SOCKETS) {
+		return (-1);
+	}
+	
+	PXE_SOCKET *sock = &pxe_sockets[socket];
+	
+	if (sock->waiting == 0)
+		return (-1);
+	
+	int	back = sock->waiting;
+	
+	PXE_FILTER_ENTRY	*entry = sock->filter;
+	
+	for ( ; back != 0; --back) {
+
+		/* filter childs are earlier */
+		entry = entry->prev;
+
+		if (entry == NULL) {
+#ifdef PXE_DEBUG
+			printf("pxe_accept(): corrupted waiting count.\n");
+#endif		
+			return (-1);
+		}
+	}
+
+	int accepted_socket = pxe_socket();
+	
+	if (accepted_socket == -1)
+		return (-1);
+		
+	/* decreasing waiting queue */
+	--sock->waiting;
+	
+	sock = &pxe_sockets[accepted_socket];
+	
+	sock->filter = entry;
+	entry->socket = sock;
+
+	return (accepted_socket);
+}
+
+void
+pxe_sock_stats()
 {
+	int		socket = 0;
+	PXE_SOCKET*	sock = pxe_sockets;
+	
+	for ( ; socket < PXE_DEFAULT_SOCKETS; ++socket, ++sock) {
+	
+		if (sock->state == PXE_SOCKET_FREE)
+			continue;
+			
+		printf("%d: filter 0x%x, recv/send: %d/%d, waiting: %d.\n ", 
+		    socket, sock->filter, sock->recv, sock->sent, sock->waiting
+		);
+	}
+}
 
-	if (!pxe_tcp_pack(socket, buf, buflen)) {
-		pxe_flush(socket);
-		pxe_tcp_pack(socket, buf, buflen);
+int
+pxe_sock_bufspace(int socket)
+{
+	if (socket > PXE_DEFAULT_SOCKETS) {
+		return (-1);
 	}
+	
+	return pxe_sockets[socket].recv_buffer.bufleft;
 }
 
 int
-pxe_recv(int socket, void *buf, size_t buflen)
+pxe_sock_place(int socket, void* data, uint16_t size)
 {
-	PXE_SOCKET *sock = &pxe_sockets[socket];
+#ifdef PXE_DEBUG_HELL
+	printf("pxe_sock_place(): sock: %d, data: 0x%x, size: %d\n", socket, data, size);
+#endif
+	if (socket > PXE_DEFAULT_SOCKETS) {
+		return (-1);
+	}
+	
+	PXE_SOCKET	*sock = &pxe_sockets[socket];
+	uint16_t 	copy_size = size;
+	
+	/* there is no enogh space available in recv buffer
+	 *   try as much as possible.
+	 */	
+	if (sock->recv_buffer.bufleft < size) {
+		
+		copy_size = sock->recv_buffer.bufleft;
+		
+		if (copy_size == 0)
+			return (0);
+	}
+		
+	pxe_memcpy(data, sock->recv_buffer.next_data, copy_size);
+	
+	sock->recv_buffer.next_data += copy_size;
+	sock->recv_buffer.bufleft -= copy_size;
+	
+	return (copy_size);
+}
 
-	if (sock->sendbuffer.leftbuf < buflen) {
+int
+pxe_sock_rewind(int socket, uint16_t size)
+{
+	if (socket > PXE_DEFAULT_SOCKETS) {
+		return (-1);
 	}
+	
+	PXE_SOCKET	*sock = &pxe_sockets[socket];
+	
+	uint16_t	rew_bytes = sock->recv_buffer.next_data - sock->recv_buffer.data;
+
+	/* if data to rewind enough, than rewing size, else only available rew_bytes */
+	if (rew_bytes > size)
+		rew_bytes = size;
+
+	sock->recv_buffer.next_data -= rew_bytes;
+	sock->recv_buffer.bufleft += rew_bytes;
+	
+	return (rew_bytes);
+}
+
+/* out:
+ *	0  - no free port
+ *	>0 - port number
+ */
+uint16_t
+pxe_next_port()
+{	/* dummy, TODO: check filters, if port used */
+    
+	if (avail_port == 40000)
+		avail_port = 1025;
+
+	return (avail_port++);
 }
-*/
 
+/* NOTE: now assuming that only UDP is implemented */
 int
-pxe_close(int socket)
+pxe_sendto(int socket, uint32_t ip, uint16_t port, void *data, uint16_t size)
 {
 
-	pxe_sockets[socket].state = PXE_TCP_CLOSED;
+#ifdef PXE_DEBUG
+	printf("pxe_sendto(): ip:port =  %8x:%d, size = %d bytes.\n", ip, port, size);
+#endif
+	if (size + sizeof(PXE_UDP_PACKET) > PXE_DEFAULT_SEND_BUFSIZE) {
+		printf("pxe_sendto(): send buffer too small for %d bytes.\n", size);
+		return (-1);
+	}
+	
+	if (!pxe_connect(socket, ip, port, PXE_UDP_PROTOCOL)) {
+		printf("pxe_sendto(): failed to connect.\n");
+		return (-1);
+	}
+	
+	PXE_SOCKET	*sock = &pxe_sockets[socket];
+	
+	/* for UDP socket, send buffer used only for one dgram */
+	PXE_UDP_PACKET	*udp_pack = (PXE_UDP_PACKET *)sock->send_buffer.data;
+	
+	/* copy user data */
+	pxe_memcpy(data, udp_pack + 1, size);
+	
+	PXE_FILTER_ENTRY *filter = sock->filter;
+
+	/* filters are useful for  incoming packet, so dst_port
+	 *  is local port.
+	 */
+	uint16_t lport = filter->dst_port;
+	
+	if (!pxe_udp_send(udp_pack, ip, port, lport, size + sizeof(PXE_UDP_PACKET), 1)) {
+		printf("pxe_sendto(): failed to send data.\n");
+		return (-1);
+	}
+	
+	return (size);
+}
+	
+
+
+int
+pxe_connect(int socket, uint32_t ip, uint16_t port, uint8_t proto)
+{
 
+	if (socket > PXE_DEFAULT_SOCKETS) {
+		return (0);
+	}
+	
+	PXE_SOCKET	*sock = &pxe_sockets[socket];
+	
+	/* socket was already initalized */
+	if (sock->filter != NULL) {
+	
+		pxe_filter_remove(sock->filter);
+		sock->filter = NULL;		/* just to be sure... */
+	}
+	
+	uint16_t lport = pxe_next_port();	/* getting free local port */
+	
+	if (port == 0) {
+		printf("pxe_connect(): failed to allocate local port.\n");
+		return (0);
+	}
+	
+	PXE_FILTER_ENTRY *entry =
+	    pxe_filter_add( ip, port, pxe_get_myip32(), lport, sock, proto);
+	    
+	
+	if ( entry == NULL ) {
+		printf("pxe_connect(): failed to add filter.\n");
+		return (0);	
+	}
+	
+	/* all is ok */
 	return (1);
 }
+
+
+int
+pxe_send(int socket, void *buf, size_t buflen)
+{
+
+	return (0);
+}
+
+int
+pxe_recv(int socket, void *buf, size_t buflen)
+{
+	
+	return (0);
+}
+
+

==== //depot/projects/soc2007/taleks-pxe_http/pxe_sock.h#4 (text+ko) ====

@@ -4,50 +4,90 @@
 #include <stdint.h>
 #include <stddef.h>
 
+#include "pxe_filter.h"
 #include "pxe_ip.h"
-
 /* buffer size choosed by default for sending/recieving*/
-#define PXE_DEFAULT_RECV_BUFSIZE         16384
-#define PXE_DEFAULT_SEND_BUFSIZE         2048
+#define PXE_DEFAULT_RECV_BUFSIZE        8192
+#define PXE_DEFAULT_SEND_BUFSIZE        2048
 /* minimal and max packet sizes to optimize tcp usage*/
-#define PXE_MIN_SEND_PACKET_SIZE    512
-#define PXE_MTU                     1500
-/* dwfault count of sockets used at the same time */
-#define PXE_DEFAULT_SOCKETS         2
+#define PXE_MIN_SEND_PACKET_SIZE        512
+#define PXE_MTU                         1500
+/* default count of sockets used at the same time */
+#define PXE_DEFAULT_SOCKETS             8
+/* default count of waiting queue */
+#define PXE_DEFAULT_WAITCOUNT           3
+/* socket states */
+#define PXE_SOCKET_FREE                 0x0
+#define PXE_SOCKET_USED                 0x1
 
 /* pxe_buffer - buffer related information */
 typedef struct pxe_buffer {
-    void	*data;      /* pointer to memory block, used for buffer*/
-    uint32_t    bufsize;    /* size of memory block */
+	void        *data;      /* pointer to memory block, used for buffer*/
+	uint32_t    bufsize;    /* size of memory block */
 
-    void	*next_data; /* pointer to next free byte in memory block*/
-    uint32_t    bufleft;    /* left buffer space */
+	void        *next_data; /* pointer to next free byte in memory block*/
+	uint32_t    bufleft;    /* left buffer space */
 } PXE_BUFFER;
 
+/* socket*/
 typedef struct pxe_socket {
-    PXE_BUFFER  send_buffer;
-    PXE_BUFFER  recv_buffer;
+	PXE_BUFFER  send_buffer;
+	PXE_BUFFER  recv_buffer;
 
-    uint32_t    sent;
-    uint32_t    recv;
-    uint8_t     state;
+	/* transmit and status counters*/
+	uint32_t    sent;
+	uint32_t    recv;
+	uint8_t     state;
+	uint8_t     waiting;		/* number of connections waiting to accept */
 
-    PXE_IPADDR  local_ip;
-    uint16_t    local_port;
+	/* for resending usage */
+	uint32_t    last_time_sent;
+	uint32_t    last_time_recv;
+	PXE_FILTER_ENTRY    *filter;	/* filter, that feeds data to this socket */
+} PXE_SOCKET;
 
-    PXE_IPADDR  remote_ip;
-    uint16_t    remote_port;
+/* inits this module */
+void	pxe_sock_init();
+/* allocates pxe_socket structure */
+int	pxe_socket_alloc();
+/* frees socket structure */
+int	pxe_socket_free(int socket);
+/* shows socket usage statistics */
+void	pxe_sock_stats();
+/* returns available space in recv buffer of socket */
+int	pxe_sock_bufspace(int socket);
+/* places data to buffer */
+int	pxe_sock_place(int socket, void* data, uint16_t size);
+/* removes data from buffer */
+int	pxe_sock_rewind(int socket, uint16_t size);
 
-    uint32_t    last_time_sent;
-    uint32_t    last_time_recv;
+/* pxe_listen() - creates "listening" socket 
+ *    it's not the same as normal listen() system call.
+ * Every pxe_listen() call creates pxe_socket structure
+ * and adds filter to filter table.
+ * WARN:
+ *	-1 - means failed
+ *	>= 0 - socket for UDP
+ *	== 0 - success for TCP
+ */
+int	pxe_listen(int socket, uint8_t proto, uint16_t port);
+/* accept awaiting connections */
+int	pxe_accept(int socket);
+/* send to provided ip/port, updating filter for socket */
+int	pxe_sendto(int socket, uint32_t ip, uint16_t port, void *data, uint16_t size);
+int	pxe_connect(int socket, uint32_t ip, uint16_t port, uint8_t proto);
 
-} PXE_SOCKET;
+/* int	pxe_listen_from(int socket, uint8_t proto, uint16_t port, uint32_t src_ip, uint16_t port, int block); */
 
-int	pxe_sockets_init();
-int	pxe_tcp_socket();
-int	pxe_connect(int socket, uint32_t ip, uint16_t port);
+/* send data to socket, blocking */
 int	pxe_send(int socket, void *buf, size_t buflen);
+/* receive data from socket, blocking  */
 int	pxe_recv(int socket, void *buf, size_t buflen);
+/* create new socket */
+int	pxe_socket();
+/* close socket */
 int	pxe_close(int socket);
+/* returns next available local port */
+uint16_t pxe_next_port();
 
 #endif // PXE_SOCK_H_INCLUDED


More information about the p4-projects mailing list