/** * @Function: void tcp_server_thread(void *arg) * @Description: stm32 wait user's connection as a server * isAccepted: a flag of accepting a user * isChecked : a flag of checking user's id */ void tcp_server_task(void *arg) { err_t err; u8 * msg_buf; static ip_addr_t ipaddr; static u16_t port; LWIP_UNUSED_ARG(arg); conn = netconn_new(NETCONN_TCP); //创建一个TCP链接 err = netconn_bind(conn,IP_ADDR_ANY,TCP_SERVER_PORT); //绑定端口 8080号端口 err = netconn_listen(conn); //进入监听模式 while (1) { printf("accepting!\n"); DEBUG_LCD(20, 160, "Accepting...... ", RED);//显示接收到的数据 err = netconn_accept(conn,&serverconn); //接收连接请求 printf("accepted!\n"); if (err == ERR_OK) //处理新连接的数据 { netconn_getaddr(serverconn,&ipaddr,&port,0); //获取远端IP地址和端口号 user_addr[3] = (uint8_t)(ipaddr.addr >> 24); user_addr[2] = (uint8_t)(ipaddr.addr>> 16); user_addr[1] = (uint8_t)(ipaddr.addr >> 8); user_addr[0] = (uint8_t)(ipaddr.addr); printf("主机%d.%d.%d.%d连接上服务器,主机端口号为:%d\r\n",user_addr[0], user_addr[1],user_addr[2],user_addr[3],port); isAccepted = 1; //已经有链接上 OSTimeDlyHMSM(0,0,3,0);//等待身份验证 while(isAccepted)//保持链接 { if(isChecked == 0)//身份确认失败 { DEBUG_LCD(20, 160, "Client Checking... ", BLUE);//显示接收到的数据 DEBUG("stm32 is cheking user's id\r\n"); OSTimeDlyHMSM(0,0,2,0); } else { DEBUG("user is checked\r\n"); // /*--------------发送任意信息给用户,确认连接状态------------------------------*/ // msg_buf = mymalloc(SRAMEX, 7); // sprintf((char *)msg_buf, "server"); // if(OSQPost(tcp_send_event, msg_buf) != OS_ERR_NONE)//为客户端信息 // { // DEBUG("OSQPost ERROR %s %d\n", __FILE__, __LINE__); // } // msg_buf = mymalloc(SRAMEX, 4);//外部内存分配空间 // sprintf((char *)msg_buf, "%c%c%c", // COMMAND_PULSE,COMMAND_SEPERATOR,COMMAND_END); // if(OSQPost(tcp_send_event,msg_buf) != OS_ERR_NONE) // { // DEBUG("OSQPost ERROR %s %d\n", __FILE__, __LINE__); // } OSTimeDlyHMSM(0,0,10,0); } OSTimeDlyHMSM(0,0,2,0); } } else {
static void http_server_serve(struct netconn *conn) { struct netbuf *inbuf; char *buf; u16_t buflen; err_t err; /* Read the data from the port, blocking if nothing yet there. We assume the request (the part we care about) is in one netbuf */ err = netconn_recv(conn, &inbuf); if (err == ERR_OK) { netbuf_data(inbuf, (void **) &buf, &buflen); ip_addr_t ip; uint16_t port; netconn_getaddr(conn, &ip, &port, 0); log_info( "Got request from %u.%u.%u.%u:%u", ip.addr & 0xFF, (ip.addr >> 8) & 0xFF, (ip.addr >> 16) & 0xFF, (ip.addr >> 24) & 0xFF, port); /* Is this an HTTP GET command? (only check the first 5 chars, since there are other formats for GET, and we're keeping it very simple )*/ if (buflen >= 5 && buf[0] == 'G' && buf[1] == 'E' && buf[2] == 'T' && buf[3] == ' ' && buf[4] == '/') { /* Send the HTML header * subtract 1 from the size, since we dont send the \0 in the string * NETCONN_NOCOPY: our data is const static, so no need to copy it */ netconn_write(conn, http_html_hdr, sizeof(http_html_hdr) - 1, NETCONN_NOCOPY); /* Send our HTML page */ netconn_write(conn, http_index_html, sizeof(http_index_html) - 1, NETCONN_NOCOPY); } }
static void data_udp_rx_serve(struct netconn *conn) { BaseSequentialStream *chp = (BaseSequentialStream *)&SD1; static uint8_t count = 0; struct netbuf *inbuf; char *buf; uint16_t buflen = 0; uint16_t i = 0; ip_addr_t my_ip; uint16_t my_port; err_t err; /* * Read the data from the port, blocking if nothing yet there. * We assume the request (the part we care about) is in one netbuf */ err = netconn_recv(conn, &inbuf); netconn_getaddr(conn, &my_ip, &my_port, local_ip); print_ip(my_ip, my_port); if (err == ERR_OK) { netbuf_data(inbuf, (void **)&buf, &buflen); chprintf(chp, "\r\nsensor rx:%d:->", count++); for(i=0; i<buflen; ++i) { chprintf(chp, "%c", buf[i]); } chprintf(chp, "\r\n"); } netconn_close(conn); /* Delete the buffer (netconn_recv gives us ownership, * so we have to make sure to deallocate the buffer) */ netbuf_delete(inbuf); }
int recvfrom(int s, void *mem, int len, unsigned int flags, struct sockaddr *from, socklen_t *fromlen) { struct lwip_socket *sock; struct skbuff *buf; u16_t buflen, copylen, off = 0; struct ip_addr *addr; u16_t port; u8_t done = 0; sock = get_socket(s); if (!sock) return -1; do { /* Check if there is data left from the last recv operation. */ if (sock->lastdata) { buf = sock->lastdata; } else { /* If this is non-blocking call, then check first */ if (((flags & MSG_DONTWAIT) || (sock->flags & O_NONBLOCK)) && !sock->rcvevent) { return -1; } /* No data was left from the previous operation, so we try to get some from the network. */ sock->lastdata = buf = netconn_recv(sock->conn); if (!buf) { /* We should really do some error checking here. */ return 0; } } buflen = netbuf_len(buf); buflen -= sock->lastoffset; if (len > buflen) { copylen = buflen; } else { copylen = len; } /* copy the contents of the received buffer into the supplied memory pointer mem */ netbuf_copy_partial(buf, (u8_t*)mem + off, copylen, sock->lastoffset); off += copylen; if (netconn_type(sock->conn) == NETCONN_TCP) { len -= copylen; if ( (len <= 0) || (buf->p->flags & PBUF_FLAG_PUSH) || !sock->rcvevent) { done = 1; } } else { done = 1; } /* If we don't peek the incoming message... */ if ((flags & MSG_PEEK)==0) { /* If this is a TCP socket, check if there is data left in the buffer. If so, it should be saved in the sock structure for next time around. */ if ((sock->conn->type == NETCONN_TCP) && (buflen - copylen > 0)) { sock->lastdata = buf; sock->lastoffset += copylen; } else { sock->lastdata = NULL; sock->lastoffset = 0; netbuf_delete(buf); } } else { done = 1; } } while (!done); /* Check to see from where the data was.*/ if (from && fromlen) { struct sockaddr_in sin; if (netconn_type(sock->conn) == NETCONN_TCP) { addr = (struct ip_addr*)&(sin.sin_addr.s_addr); netconn_getaddr(sock->conn, addr, &port, 0); } else { addr = netbuf_fromaddr(buf); port = netbuf_fromport(buf); } memset(&sin, 0, sizeof(sin)); sin.sin_len = sizeof(sin); sin.sin_family = AF_INET; sin.sin_port = htons(port); sin.sin_addr.s_addr = addr->addr; if (*fromlen > sizeof(sin)) *fromlen = sizeof(sin); SMEMCPY(from, &sin, *fromlen); } return off; }
msg_t data_udp_send_thread(void *p) { void * arg __attribute__ ((unused)) = p; BaseSequentialStream *chp = (BaseSequentialStream *)&SD1; err_t err; uint8_t count = 0; struct netconn *conn; struct netbuf *buf; char* data; char msg[DATA_UDP_MSG_SIZE] ; ip_addr_t ip_addr_rnet; ip_addr_t ip_addr_fc; ip_addr_t my_ip; uint16_t my_port; RNET_A_IP_ADDR(&ip_addr_rnet); IP_PSAS_FC(&ip_addr_fc); chRegSetThreadName("data_udp_send_thread"); conn = netconn_new( NETCONN_UDP ); chThdSleepMilliseconds(1000); chprintf(chp, "Start udp send thread\n\r"); /* Bind to the local address, or to ANY address */ // netconn_bind(conn, NULL, DATA_UDP_TX_THREAD_PORT ); //local port, NULL is bind to ALL ADDRESSES! (IP_ADDR_ANY) err = netconn_bind(conn, &ip_addr_rnet, RNET_A_TX_PORT ); //local port netconn_getaddr(conn, &my_ip, &my_port, local_ip); print_ip(my_ip, my_port); if (err == ERR_OK) { /* Connect to specific address or a broadcast address */ /* * \todo Understand why a UDP needs a connect... * This may be a LwIP thing that chooses between tcp_/udp_/raw_ connections internally. * */ // netconn_connect(conn, IP_ADDR_BROADCAST, DATA_UDP_TX_THREAD_PORT ); // err = netconn_connect(conn, &ip_addr_fc, FC_LISTEN_PORT_RNET_A ); err = netconn_connect(conn, IP_ADDR_BROADCAST, FC_LISTEN_PORT_RNET_A ); if(err == ERR_OK) { for( ;; ){ buf = netbuf_new(); data = netbuf_alloc(buf, sizeof(msg)); sprintf(msg, "rnet tx: %d", count++); memcpy (data, msg, sizeof (msg)); err = netconn_send(conn, buf); // chprintf(chp, "rnet sent: index: %d. Error: %d\r\n", count, err); netbuf_delete(buf); // De-allocate packet buffer chThdSleepMilliseconds(500); } return RDY_OK; } else { return RDY_RESET; } } else { return RDY_RESET; } }