PageRenderTime 109ms CodeModel.GetById 47ms app.highlight 57ms RepoModel.GetById 1ms app.codeStats 1ms

/g-bios/lib/net/socket.c

https://github.com/wuyohee2004/learn
C | 726 lines | 552 code | 155 blank | 19 comment | 127 complexity | 39c6823dd284ddfa0529edfa53b83cac MD5 | raw file
  1#include <stdio.h>
  2#include <errno.h>
  3#include <string.h>
  4#include <malloc.h>
  5#include <assert.h>
  6#include <delay.h>
  7#include <net/net.h>
  8#include <net/skb.h>
  9#include <fs.h>
 10#include <uart/uart.h> // fixme: to be removed
 11
 12#define MAX_SOCK_NUM  32
 13
 14static struct socket *g_sock_fds[MAX_SOCK_NUM];
 15
 16static inline struct socket *get_sock(int fd)
 17{
 18	if (fd <= 0 || fd >= MAX_SOCK_NUM)
 19		return NULL;
 20
 21	return g_sock_fds[fd];
 22}
 23
 24#define PORT_MIN 50000
 25
 26static inline __u16 port_alloc(int type)
 27{
 28	static __u16 port = PORT_MIN;
 29
 30	port++;
 31	if (port < PORT_MIN)
 32		port = PORT_MIN;
 33
 34	return port;
 35}
 36
 37static inline void port_free(__u16 port)
 38{
 39}
 40
 41static int tcp_wait_for_state(const struct socket *sock, enum tcp_state state)
 42{
 43	int to;
 44
 45	for (to = 0; to < 100; to++) {
 46		ndev_poll();
 47		if (sock->state == state)
 48			return 0;
 49
 50		mdelay(100);
 51	}
 52
 53	return -ETIMEDOUT;
 54}
 55
 56int socket_ioctl(int fd, int cmd, int flags)
 57{
 58	struct socket *sock;
 59
 60	sock = get_sock(fd);
 61	if (NULL == sock)
 62		return -ENOENT;
 63
 64	switch (cmd) {
 65	case SKIOCS_FLAGS:
 66		sock->obstruct_flags = flags;
 67		break;
 68
 69	default:
 70		return -EINVAL;
 71	}
 72
 73	return 0;
 74}
 75static struct sock_buff *sock_recv_packet(struct socket *sock)
 76{
 77	__UNUSED__ __u32 psr;
 78	struct sock_buff *skb;
 79	struct list_head *first;
 80	int to = 10000; // timeout
 81	int ret;
 82	char key;
 83
 84	while (1) {
 85		ret = uart_read(CONFIG_UART_INDEX, (__u8 *)&key, 1, WAIT_ASYNC);
 86		if (ret > 0 && key == CHAR_CTRL_C)
 87			return NULL;
 88
 89		ndev_poll();
 90
 91		lock_irq_psr(psr);
 92		if (!list_empty(&sock->rx_qu)) {
 93			unlock_irq_psr(psr);
 94			break;
 95		}
 96		unlock_irq_psr(psr);
 97
 98		if (sock->obstruct_flags == 1) {
 99			to--;
100			if (to == 0)
101				break;
102		}
103
104		udelay(1000);
105	}
106
107	if (to > 0) {
108		lock_irq_psr(psr);
109		first = sock->rx_qu.next;
110		list_del(first);
111		unlock_irq_psr(psr);
112
113		skb = container_of(first, struct sock_buff, node);
114		return skb;
115	}
116
117	return NULL;
118}
119
120// fixme: to be removed
121int qu_is_empty(int fd)
122{
123	__u32 __UNUSED__ psr;
124	struct socket *sock;
125
126	sock = get_sock(fd);
127	if (NULL == sock)
128		return 1;
129
130	ndev_poll();
131
132	lock_irq_psr(psr);
133	if (!list_empty(&sock->rx_qu)) {
134		unlock_irq_psr(psr);
135		return 0;
136	}
137	unlock_irq_psr(psr);
138
139	return 1;
140}
141
142int socket(int domain, int type, int protocol)
143{
144	int fd;
145	struct socket *sock;
146
147	for (fd = 1; fd < MAX_SOCK_NUM; fd++) {
148		if (NULL == g_sock_fds[fd])
149			goto alloc_sock;
150	}
151
152	return -ENODEV;
153
154alloc_sock:
155	sock = malloc(sizeof(struct socket));
156
157	if (NULL == sock) {
158		DPRINT("%s: fail to alloc socket!\n", __func__);
159		return -ENOMEM;
160	}
161
162	sock->type = type;
163	if (SOCK_STREAM == type) { // fixme
164		sock->state = TCPS_CLOSED;
165		sock->seq_num = 1; // fixme
166		sock->ack_num = 0;
167	}
168	memset(sock->saddr, 0, sizeof(sock->saddr));
169	INIT_LIST_HEAD(&sock->tx_qu);
170	INIT_LIST_HEAD(&sock->rx_qu);
171	sock->protocol = protocol;
172
173	g_sock_fds[fd] = sock;
174
175	return fd;
176}
177
178static void free_skb_list(struct list_head *qu)
179{
180	struct list_head *first;
181	struct sock_buff *skb;
182
183	while (!list_empty(qu)) {
184		first = qu->next;
185
186		list_del(first);
187		skb = container_of(first, struct sock_buff, node);
188		skb_free(skb);
189	}
190}
191
192int sk_close(int fd)
193{
194	int ret;
195	unsigned long __UNUSED__ cpsr;
196	struct socket *sock;
197	struct sock_buff *skb;
198
199	sock = get_sock(fd);
200	if (NULL == sock)
201		return -EINVAL;
202
203	if (TCPS_ESTABLISHED == sock->state || \
204		TCPS_SYN_RCVD == sock->state || \
205		TCPS_CLOSE_WAIT == sock->state) {
206		enum tcp_state last_state;
207
208		skb = skb_alloc(ETH_HDR_LEN + IP_HDR_LEN + TCP_HDR_LEN, 0);
209		// if null
210		skb->sock = sock;
211
212		lock_irq_psr(cpsr);
213		tcp_send_packet(skb, FLG_FIN | FLG_ACK, NULL);
214		if (TCPS_CLOSE_WAIT == sock->state)
215			sock->state = TCPS_LAST_ACK;
216		else
217			sock->state = TCPS_FIN_WAIT1;
218		last_state = sock->state;
219		unlock_irq_psr(cpsr);
220
221		if (TCPS_LAST_ACK == last_state)
222			ret = tcp_wait_for_state(sock, TCPS_CLOSED);
223		else
224			ret = tcp_wait_for_state(sock, TCPS_TIME_WAIT);
225
226		if (ret < 0)
227			return ret;
228	}
229
230	// fixme
231	if (TCPS_TIME_WAIT == sock->state) {
232		ret = tcp_wait_for_state(sock, TCPS_CLOSED);
233		if (ret < 0)
234			sock->state = TCPS_CLOSED;
235	}
236
237	if (TCPS_CLOSED == sock->state) {
238		lock_irq_psr(cpsr);
239		free_skb_list(&sock->rx_qu);
240		free_skb_list(&sock->tx_qu);
241		free(sock);
242		unlock_irq_psr(cpsr);
243		g_sock_fds[fd] = NULL;
244	} else {
245		printf("%s(): Warning! (state = %d)\n", __func__, sock->state);
246		return -EINVAL;
247	}
248
249	return 0;
250}
251
252struct eth_addr *gethostaddr(const __u32 nip)
253{
254	__u32 count = 0;
255	struct eth_addr *remote_addr;
256
257	arp_send_packet((__u8 *)&nip, NULL, ARP_OP_REQ);
258
259	while (count < 100000) {
260		int ret;
261		__u8  key;
262
263		ret = uart_read(CONFIG_UART_INDEX, &key, 1, WAIT_ASYNC);
264		if (ret > 0 && key == CHAR_CTRL_C)
265			return NULL;
266
267		ndev_poll();
268
269		remote_addr = getaddr(nip);
270		if (remote_addr)
271			break;
272
273		// TODO: add re-send code here
274		udelay(3);
275		count++;
276	}
277
278	return remote_addr;
279}
280
281int bind(int fd, const struct sockaddr *addr, socklen_t len)
282{
283	int ret = 0;
284	struct socket *sock;
285	const struct sockaddr_in *sa;
286	struct sockaddr_in *sin;
287	struct net_device *ndev;
288
289	sock = get_sock(fd);
290	if (NULL == sock) {
291		// printf
292		return -EINVAL;
293	}
294	sin = &sock->saddr[SA_SRC];
295
296	sin->sin_family = addr->sa_family;
297
298	switch (addr->sa_family) {
299	case AF_INET:
300		sa = (const struct sockaddr_in *)addr;
301
302		sin->sin_port = sa->sin_port ? sa->sin_port : htons(port_alloc(sock->type));
303
304		if (sa->sin_addr.s_addr == htonl(INADDR_ANY)) {
305			// fixme: to find the best ndev
306			ndev = ndev_get_first();
307			sin->sin_addr.s_addr = ndev->ip;
308		} else {
309			sin->sin_addr = sa->sin_addr;
310		}
311
312		break;
313
314	// TODO: support other address families here
315
316	default:
317		return -ENOTSUPP;
318	}
319
320	return ret;
321}
322
323//
324ssize_t sendto(int fd, const void *buff, __u32 buff_size, int flags,
325			const struct sockaddr *dest_addr, socklen_t addr_size)
326{
327	struct socket *sock;
328	struct sock_buff *skb;
329
330	sock = get_sock(fd);
331
332	if (NULL == sock) {
333		// printf
334		return -EINVAL;
335	}
336
337	memcpy(&sock->saddr[SA_DST], dest_addr, addr_size);
338
339	switch (sock->type) {
340	case SOCK_RAW:
341		if (PROT_ICMP == sock->protocol) {
342			skb = skb_alloc(ETH_HDR_LEN + IP_HDR_LEN, buff_size);
343			skb->sock = sock;
344			memcpy(skb->data, buff, buff_size);
345			ip_send_packet(skb, PROT_ICMP);
346			break;
347		} else if (PROT_ETH == sock->protocol) {
348			arp_send_packet((__u8 *)&sock->saddr[SA_DST].sin_addr.s_addr, NULL, ARP_OP_REQ);
349			break;
350		}
351
352	case SOCK_DGRAM:
353		skb = skb_alloc(ETH_HDR_LEN + IP_HDR_LEN + UDP_HDR_LEN, buff_size);
354		skb->sock = sock;
355		memcpy(skb->data, buff, buff_size);
356		udp_send_packet(skb);
357		break;
358	}
359
360	return buff_size;
361}
362
363ssize_t recvfrom(int fd, void *buf, __u32 n, int flags,
364		struct sockaddr *src_addr, socklen_t *addrlen)
365{
366	struct socket *sock;
367	struct sock_buff *skb = NULL;
368	__u32 pkt_len;
369
370	sock = get_sock(fd);
371	if (NULL == sock)
372		return -EINVAL;
373
374	skb = sock_recv_packet(sock);
375	if(NULL == skb)
376		return 0;
377
378	// fixme !
379	pkt_len = min(skb->size, n);
380	memcpy(buf, skb->data, pkt_len);
381
382	*addrlen = sizeof(struct sockaddr_in);
383	memcpy(src_addr, &sock->saddr[SA_DST], *addrlen);
384
385	skb_free(skb);
386
387	return pkt_len;
388}
389
390#if 0
391static void tcp_make_option(__u8 *opt, __u16 size)
392{
393	__u32 tsv = htonl(3455994), tser = 0;
394
395	if (size > 0) {
396	memset(opt, 0, size);
397
398#if 1
399	// MSS
400	*opt++ = 2;
401	*opt++ = 4;
402	*(__u16 *)opt = htons(1460);
403	opt += 2;
404#endif
405
406#if 1
407	// SACK
408	*opt++ = 4;
409	*opt++ = 2;
410#endif
411
412#if 1
413	// Time stamp
414	*opt++ = 8;
415	*opt++ = 10;
416	memcpy(opt, &tsv, 4);
417	opt += 4;
418	memcpy(opt, &tser, 4);
419	opt += 4;
420#endif
421
422#if 1
423	// NOP
424	*opt++ = 1;
425#endif
426
427#if 1
428	// WS
429	*opt++ = 3;
430	*opt++ = 3;
431	*opt++ = 5;
432#endif
433	}
434}
435#endif
436
437int connect(int fd, const struct sockaddr *addr, socklen_t len)
438{
439	int ret;
440	__UNUSED__ __u32 psr;
441	struct socket *sock;
442	struct sock_buff *skb;
443
444	sock = get_sock(fd);
445	if (NULL == sock) {
446		// DPRINT
447		return -ENOENT;
448	}
449
450	memcpy(&sock->saddr[SA_DST], addr, len);
451
452	// SYN
453	skb = skb_alloc(ETH_HDR_LEN + IP_HDR_LEN + TCP_HDR_LEN, 0);
454	// if null
455	skb->sock = sock;
456
457	lock_irq_psr(psr);
458	tcp_send_packet(skb, FLG_SYN, NULL);
459	sock->state = TCPS_SYN_SENT;
460	unlock_irq_psr(psr);
461
462	ret = tcp_wait_for_state(sock, TCPS_ESTABLISHED);
463
464	if (ret < 0)
465		sock->state = TCPS_CLOSED;
466
467	return ret;
468}
469
470ssize_t send(int fd, const void *buf, size_t n, int flag)
471{
472	struct socket *sock;
473	struct sock_buff *skb;
474
475	sock = get_sock(fd);
476	if (NULL == sock)
477		return -EINVAL;
478
479	if (TCPS_ESTABLISHED != sock->state)
480		return -EIO;
481
482	skb = skb_alloc(ETH_HDR_LEN + IP_HDR_LEN + TCP_HDR_LEN, n);
483	// if null
484	skb->sock = sock;
485	memcpy(skb->data, buf, n);
486
487	tcp_send_packet(skb, FLG_PSH | FLG_ACK, NULL);
488
489#if 0
490	for (time_out = 0; time_out < 10; time_out++) {
491		ndev_poll();
492		if (sock->state == 1)
493			break;
494
495		mdelay(100);
496		printf("%s() line %d\n", __func__, __LINE__);
497	}
498#endif
499
500	return n;
501}
502
503ssize_t recv(int fd, void *buf, size_t n, int flag)
504{
505	ssize_t pkt_len;
506	struct socket *sock;
507	struct sock_buff *skb;
508
509	sock = get_sock(fd);
510	if (NULL == sock)
511		return -ENOENT;
512
513	if (TCPS_ESTABLISHED != sock->state)
514		return -EIO;
515
516	skb = sock_recv_packet(sock);
517	if (skb == NULL)
518		return -EIO;
519
520	pkt_len = skb->size <= n ? skb->size : n;
521	memcpy(buf, skb->data, pkt_len);
522
523	skb_free(skb);
524
525	return pkt_len;
526}
527
528struct socket *tcp_search_socket(const struct tcp_header *tcp_pkt, const struct ip_header *ip_pkt)
529{
530	int fd;
531	struct socket *sock;
532	struct sockaddr_in *saddr;
533
534	for (fd = 1; fd < MAX_SOCK_NUM; fd++) {
535		sock = g_sock_fds[fd];
536
537		if (NULL == sock)
538			continue;
539
540		saddr = &sock->saddr[SA_SRC];
541
542		if (sock->type != SOCK_STREAM)
543			continue;
544
545#if 0
546		if (memcmp(saddr->sin_addr, ip_pkt->src_ip, 4) != 0) {
547			printf("sock = 0x%x, des ip is %d (NOT %d.%d.%d.%d, %02x.%02x.%02x.%02x.%02x.%02x)\n",
548				saddr,
549				ip_pkt->src_ip[3],
550				saddr->des_ip[0],
551				saddr->des_ip[1],
552				saddr->des_ip[2],
553				saddr->des_ip[3],
554				saddr->des_mac[0],
555				saddr->des_mac[1],
556				saddr->des_mac[2],
557				saddr->des_mac[3],
558				saddr->des_mac[4],
559				saddr->des_mac[5]
560				);
561			continue;
562		}
563#endif
564
565		if (saddr->sin_port != tcp_pkt->dst_port) {
566#if 0
567			printf("from %d, src port: 0x%x != 0x%x\n", ip_pkt->src_ip[3], ntohs(saddr->src_port), BE16_TO_CPU(tcp_pkt->dst_port));
568#endif
569			continue;
570		}
571
572#if 0
573		if (memcmp(&src_ip, ip_pkt->des_ip, 4) != 0) {
574			printf("src ip: %d.%d.%d.%d\n",
575				ip_pkt->des_ip[0],
576				ip_pkt->des_ip[1],
577				ip_pkt->des_ip[2],
578				ip_pkt->des_ip[3]
579				);
580
581			continue;
582		}
583#endif
584
585#if 0
586		memcmp(&sock->saddr[SA_DST].sin_addr, ip_hdr->src_ip, IPV4_ADR_LEN);
587		memcmp(sock->saddr[SA_DST].sin_port = tcp_hdr->src_port);
588#endif
589
590		return sock;
591	}
592
593	return NULL;
594}
595
596struct socket *udp_search_socket(const struct udp_header *udp_pkt, const struct ip_header *ip_pkt)
597{
598	int fd;
599	struct socket *sock;
600	struct sockaddr_in *saddr;
601#if 0
602	__u32 src_ip;
603
604	ndev_ioctl(NULL, NIOC_GET_IP, &src_ip);
605#endif
606
607	for (fd = 1; fd < MAX_SOCK_NUM; fd++) {
608		sock = g_sock_fds[fd];
609
610		if (NULL == sock)
611			continue;
612
613		saddr = &sock->saddr[SA_SRC];
614
615		if (sock->type != SOCK_DGRAM)
616			continue;
617
618#if 0
619		if (memcmp(saddr->sin_addr, ip_pkt->src_ip, 4) != 0) {
620			printf("sock = 0x%x, des ip is %d (NOT %d.%d.%d.%d, %02x.%02x.%02x.%02x.%02x.%02x)\n",
621				saddr,
622				ip_pkt->src_ip[3],
623				saddr->des_ip[0],
624				saddr->des_ip[1],
625				saddr->des_ip[2],
626				saddr->des_ip[3],
627				saddr->des_mac[0],
628				saddr->des_mac[1],
629				saddr->des_mac[2],
630				saddr->des_mac[3],
631				saddr->des_mac[4],
632				saddr->des_mac[5]
633				);
634			continue;
635		}
636#endif
637
638		if (saddr->sin_port != udp_pkt->dst_port) {
639#if 0
640			printf("from %d, src port: 0x%x != 0x%x\n", ip_pkt->src_ip[3], ntohs(saddr->src_port), BE16_TO_CPU(udp_pkt->dst_port));
641#endif
642			continue;
643		}
644
645#if 0
646		if (memcmp(&src_ip, ip_pkt->des_ip, 4) != 0) {
647			printf("src ip: %d.%d.%d.%d\n",
648				ip_pkt->des_ip[0],
649				ip_pkt->des_ip[1],
650				ip_pkt->des_ip[2],
651				ip_pkt->des_ip[3]
652				);
653
654			continue;
655		}
656#endif
657
658		return sock;
659	}
660
661	return NULL;
662}
663
664
665struct socket *icmp_search_socket(const struct ping_packet *ping_pkt, const struct ip_header *ip_pkt)
666{
667	int fd;
668	struct socket *sock;
669#if 0
670	__u32 src_ip;
671
672	ndev_ioctl(NULL, NIOC_GET_IP, &src_ip);
673#endif
674
675	for (fd = 1; fd < MAX_SOCK_NUM; fd++) {
676		sock = g_sock_fds[fd];
677
678		if (NULL == sock)
679			continue;
680
681		if (sock->type != SOCK_RAW)
682			continue;
683
684		if (memcmp(&sock->saddr[SA_DST].sin_addr.s_addr, ip_pkt->src_ip, 4))
685			continue;
686#if 0
687		if (memcmp(&src_ip, ip_pkt->des_ip, 4) != 0) {
688			printf("src ip: %d.%d.%d.%d\n",
689				ip_pkt->des_ip[0],
690				ip_pkt->des_ip[1],
691				ip_pkt->des_ip[2],
692				ip_pkt->des_ip[3]
693				);
694
695			continue;
696		}
697#endif
698
699		return sock;
700	}
701
702	return NULL;
703}
704
705struct socket *arp_search_socket(const struct arp_packet *arp_pkt)
706{
707	int fd;
708	struct socket *sock;
709
710	for (fd = 1; fd < MAX_SOCK_NUM; fd++)	{
711		sock = g_sock_fds[fd];
712
713		if (NULL == sock)
714			continue;
715
716		if (sock->type != SOCK_RAW || PROT_ETH != sock->protocol)
717			continue;
718
719		if (memcmp(&sock->saddr[SA_DST].sin_addr.s_addr, arp_pkt->src_ip, 4))
720			continue;
721
722		return sock;
723	}
724
725	return NULL;
726}