1 // SPDX-License-Identifier: GPL-2.0-or-later
2 /*
3 * Copyright (c) 2022 Huawei Device Co., Ltd.
4 *
5 * Description: Demo example of NewIP udp server.
6 *
7 * Author: Yang Yanjun <yangyanjun@huawei.com>
8 *
9 * Data: 2022-09-06
10 */
11 #include <stdio.h>
12 #include <stdlib.h>
13 #include <unistd.h>
14 #include <string.h>
15 #include <arpa/inet.h>
16 #include <sys/types.h>
17 #include <sys/socket.h>
18
19 #define __USE_GNU
20 #include <sched.h>
21 #include <pthread.h>
22
23 #include "nip_uapi.h"
24 #include "nip_lib.h"
25 #include "newip_route.h"
26
recv_send(void * args)27 static void *recv_send(void *args)
28 {
29 char buf[BUFLEN] = {0};
30 int fd;
31 ssize_t recv_num, ret;
32 int count = 0;
33 socklen_t slen;
34 struct sockaddr_nin si_remote;
35
36 memcpy(&fd, args, sizeof(int));
37 while (count < PKTCNT) {
38 slen = sizeof(si_remote);
39 memset(buf, 0, sizeof(char) * BUFLEN);
40 memset(&si_remote, 0, sizeof(si_remote));
41 recv_num = recvfrom(fd, buf, BUFLEN, 0, (struct sockaddr *)&si_remote, &slen);
42 if (recv_num < 0) {
43 printf("server recvfrom fail, recv_num=%zd\n", recv_num);
44 goto END;
45 } else if (recv_num == 0) { /* no data */
46 ;
47 } else {
48 printf("Received -- %s -- from 0x%x:%d\n", buf,
49 si_remote.sin_addr.NIP_ADDR_FIELD16[0], ntohs(si_remote.sin_port));
50 slen = sizeof(si_remote);
51 ret = sendto(fd, buf, BUFLEN, 0, (struct sockaddr *)&si_remote, slen);
52 if (ret < 0) {
53 printf("server sendto fail, ret=%zd\n", ret);
54 goto END;
55 }
56 printf("Sending -- %s -- to 0x%0x:%d\n", buf,
57 si_remote.sin_addr.NIP_ADDR_FIELD8[0], ntohs(si_remote.sin_port));
58 }
59 count++;
60 }
61 END: return NULL;
62 }
63
main(int argc,char ** argv)64 int main(int argc, char **argv)
65 {
66 int fd;
67 pthread_t th;
68 struct sockaddr_nin si_local;
69
70 fd = socket(AF_NINET, SOCK_DGRAM, IPPROTO_UDP);
71 if (fd < 0) {
72 perror("socket");
73 return -1;
74 }
75
76 memset((char *)&si_local, 0, sizeof(si_local));
77 si_local.sin_family = AF_NINET;
78 si_local.sin_port = htons(UDP_SERVER_PORT);
79 // 2-byte address of the server: 0xDE00
80 si_local.sin_addr.NIP_ADDR_FIELD8[INDEX_0] = 0xDE;
81 si_local.sin_addr.NIP_ADDR_FIELD8[INDEX_1] = 0x00;
82 si_local.sin_addr.bitlen = NIP_ADDR_BIT_LEN_16; // 2-byte: 16bit
83
84 if (bind(fd, (const struct sockaddr *)&si_local, sizeof(si_local)) < 0) {
85 perror("bind");
86 goto END;
87 }
88
89 printf("bind success, addr=0x%02x%02x, port=%d\n",
90 si_local.sin_addr.NIP_ADDR_FIELD8[INDEX_0],
91 si_local.sin_addr.NIP_ADDR_FIELD8[INDEX_1], UDP_SERVER_PORT);
92
93 pthread_create(&th, NULL, recv_send, &fd);
94 /* Wait for the thread to end and synchronize operations between threads */
95 pthread_join(th, NULL);
96
97 END: close(fd);
98 return 0;
99 }
100
101