Modify changes to test TCP socket.
Fork of lwip by
api/api_lib.c@12:963887732b7c, 2013-12-13 (annotated)
- Committer:
- rebonatto
- Date:
- Fri Dec 13 11:39:39 2013 +0000
- Revision:
- 12:963887732b7c
- Parent:
- 0:51ac1d130fd4
modify;
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
mbed_official | 0:51ac1d130fd4 | 1 | /** |
mbed_official | 0:51ac1d130fd4 | 2 | * @file |
mbed_official | 0:51ac1d130fd4 | 3 | * Sequential API External module |
mbed_official | 0:51ac1d130fd4 | 4 | * |
mbed_official | 0:51ac1d130fd4 | 5 | */ |
mbed_official | 0:51ac1d130fd4 | 6 | |
mbed_official | 0:51ac1d130fd4 | 7 | /* |
mbed_official | 0:51ac1d130fd4 | 8 | * Copyright (c) 2001-2004 Swedish Institute of Computer Science. |
mbed_official | 0:51ac1d130fd4 | 9 | * All rights reserved. |
mbed_official | 0:51ac1d130fd4 | 10 | * |
mbed_official | 0:51ac1d130fd4 | 11 | * Redistribution and use in source and binary forms, with or without modification, |
mbed_official | 0:51ac1d130fd4 | 12 | * are permitted provided that the following conditions are met: |
mbed_official | 0:51ac1d130fd4 | 13 | * |
mbed_official | 0:51ac1d130fd4 | 14 | * 1. Redistributions of source code must retain the above copyright notice, |
mbed_official | 0:51ac1d130fd4 | 15 | * this list of conditions and the following disclaimer. |
mbed_official | 0:51ac1d130fd4 | 16 | * 2. Redistributions in binary form must reproduce the above copyright notice, |
mbed_official | 0:51ac1d130fd4 | 17 | * this list of conditions and the following disclaimer in the documentation |
mbed_official | 0:51ac1d130fd4 | 18 | * and/or other materials provided with the distribution. |
mbed_official | 0:51ac1d130fd4 | 19 | * 3. The name of the author may not be used to endorse or promote products |
mbed_official | 0:51ac1d130fd4 | 20 | * derived from this software without specific prior written permission. |
mbed_official | 0:51ac1d130fd4 | 21 | * |
mbed_official | 0:51ac1d130fd4 | 22 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED |
mbed_official | 0:51ac1d130fd4 | 23 | * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF |
mbed_official | 0:51ac1d130fd4 | 24 | * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT |
mbed_official | 0:51ac1d130fd4 | 25 | * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, |
mbed_official | 0:51ac1d130fd4 | 26 | * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT |
mbed_official | 0:51ac1d130fd4 | 27 | * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
mbed_official | 0:51ac1d130fd4 | 28 | * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
mbed_official | 0:51ac1d130fd4 | 29 | * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING |
mbed_official | 0:51ac1d130fd4 | 30 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY |
mbed_official | 0:51ac1d130fd4 | 31 | * OF SUCH DAMAGE. |
mbed_official | 0:51ac1d130fd4 | 32 | * |
mbed_official | 0:51ac1d130fd4 | 33 | * This file is part of the lwIP TCP/IP stack. |
mbed_official | 0:51ac1d130fd4 | 34 | * |
mbed_official | 0:51ac1d130fd4 | 35 | * Author: Adam Dunkels <adam@sics.se> |
mbed_official | 0:51ac1d130fd4 | 36 | * |
mbed_official | 0:51ac1d130fd4 | 37 | */ |
mbed_official | 0:51ac1d130fd4 | 38 | |
mbed_official | 0:51ac1d130fd4 | 39 | /* This is the part of the API that is linked with |
mbed_official | 0:51ac1d130fd4 | 40 | the application */ |
mbed_official | 0:51ac1d130fd4 | 41 | |
mbed_official | 0:51ac1d130fd4 | 42 | #include "lwip/opt.h" |
mbed_official | 0:51ac1d130fd4 | 43 | |
mbed_official | 0:51ac1d130fd4 | 44 | #if LWIP_NETCONN /* don't build if not configured for use in lwipopts.h */ |
mbed_official | 0:51ac1d130fd4 | 45 | |
mbed_official | 0:51ac1d130fd4 | 46 | #include "lwip/api.h" |
mbed_official | 0:51ac1d130fd4 | 47 | #include "lwip/tcpip.h" |
mbed_official | 0:51ac1d130fd4 | 48 | #include "lwip/memp.h" |
mbed_official | 0:51ac1d130fd4 | 49 | |
mbed_official | 0:51ac1d130fd4 | 50 | #include "lwip/ip.h" |
mbed_official | 0:51ac1d130fd4 | 51 | #include "lwip/raw.h" |
mbed_official | 0:51ac1d130fd4 | 52 | #include "lwip/udp.h" |
mbed_official | 0:51ac1d130fd4 | 53 | #include "lwip/tcp.h" |
mbed_official | 0:51ac1d130fd4 | 54 | |
mbed_official | 0:51ac1d130fd4 | 55 | #include <string.h> |
rebonatto | 12:963887732b7c | 56 | #include <stdio.h> |
mbed_official | 0:51ac1d130fd4 | 57 | |
mbed_official | 0:51ac1d130fd4 | 58 | /** |
mbed_official | 0:51ac1d130fd4 | 59 | * Create a new netconn (of a specific type) that has a callback function. |
mbed_official | 0:51ac1d130fd4 | 60 | * The corresponding pcb is also created. |
mbed_official | 0:51ac1d130fd4 | 61 | * |
mbed_official | 0:51ac1d130fd4 | 62 | * @param t the type of 'connection' to create (@see enum netconn_type) |
mbed_official | 0:51ac1d130fd4 | 63 | * @param proto the IP protocol for RAW IP pcbs |
mbed_official | 0:51ac1d130fd4 | 64 | * @param callback a function to call on status changes (RX available, TX'ed) |
mbed_official | 0:51ac1d130fd4 | 65 | * @return a newly allocated struct netconn or |
mbed_official | 0:51ac1d130fd4 | 66 | * NULL on memory error |
mbed_official | 0:51ac1d130fd4 | 67 | */ |
mbed_official | 0:51ac1d130fd4 | 68 | struct netconn* |
mbed_official | 0:51ac1d130fd4 | 69 | netconn_new_with_proto_and_callback(enum netconn_type t, u8_t proto, netconn_callback callback) |
mbed_official | 0:51ac1d130fd4 | 70 | { |
mbed_official | 0:51ac1d130fd4 | 71 | struct netconn *conn; |
mbed_official | 0:51ac1d130fd4 | 72 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 73 | |
mbed_official | 0:51ac1d130fd4 | 74 | conn = netconn_alloc(t, callback); |
mbed_official | 0:51ac1d130fd4 | 75 | if (conn != NULL) { |
mbed_official | 0:51ac1d130fd4 | 76 | msg.function = do_newconn; |
mbed_official | 0:51ac1d130fd4 | 77 | msg.msg.msg.n.proto = proto; |
mbed_official | 0:51ac1d130fd4 | 78 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 79 | if (TCPIP_APIMSG(&msg) != ERR_OK) { |
mbed_official | 0:51ac1d130fd4 | 80 | LWIP_ASSERT("freeing conn without freeing pcb", conn->pcb.tcp == NULL); |
mbed_official | 0:51ac1d130fd4 | 81 | LWIP_ASSERT("conn has no op_completed", sys_sem_valid(&conn->op_completed)); |
mbed_official | 0:51ac1d130fd4 | 82 | LWIP_ASSERT("conn has no recvmbox", sys_mbox_valid(&conn->recvmbox)); |
mbed_official | 0:51ac1d130fd4 | 83 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 84 | LWIP_ASSERT("conn->acceptmbox shouldn't exist", !sys_mbox_valid(&conn->acceptmbox)); |
mbed_official | 0:51ac1d130fd4 | 85 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 86 | sys_sem_free(&conn->op_completed); |
mbed_official | 0:51ac1d130fd4 | 87 | sys_mbox_free(&conn->recvmbox); |
mbed_official | 0:51ac1d130fd4 | 88 | memp_free(MEMP_NETCONN, conn); |
mbed_official | 0:51ac1d130fd4 | 89 | return NULL; |
mbed_official | 0:51ac1d130fd4 | 90 | } |
mbed_official | 0:51ac1d130fd4 | 91 | } |
mbed_official | 0:51ac1d130fd4 | 92 | return conn; |
mbed_official | 0:51ac1d130fd4 | 93 | } |
mbed_official | 0:51ac1d130fd4 | 94 | |
mbed_official | 0:51ac1d130fd4 | 95 | /** |
mbed_official | 0:51ac1d130fd4 | 96 | * Close a netconn 'connection' and free its resources. |
mbed_official | 0:51ac1d130fd4 | 97 | * UDP and RAW connection are completely closed, TCP pcbs might still be in a waitstate |
mbed_official | 0:51ac1d130fd4 | 98 | * after this returns. |
mbed_official | 0:51ac1d130fd4 | 99 | * |
mbed_official | 0:51ac1d130fd4 | 100 | * @param conn the netconn to delete |
mbed_official | 0:51ac1d130fd4 | 101 | * @return ERR_OK if the connection was deleted |
mbed_official | 0:51ac1d130fd4 | 102 | */ |
mbed_official | 0:51ac1d130fd4 | 103 | err_t |
mbed_official | 0:51ac1d130fd4 | 104 | netconn_delete(struct netconn *conn) |
mbed_official | 0:51ac1d130fd4 | 105 | { |
mbed_official | 0:51ac1d130fd4 | 106 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 107 | |
mbed_official | 0:51ac1d130fd4 | 108 | /* No ASSERT here because possible to get a (conn == NULL) if we got an accept error */ |
mbed_official | 0:51ac1d130fd4 | 109 | if (conn == NULL) { |
mbed_official | 0:51ac1d130fd4 | 110 | return ERR_OK; |
mbed_official | 0:51ac1d130fd4 | 111 | } |
mbed_official | 0:51ac1d130fd4 | 112 | |
mbed_official | 0:51ac1d130fd4 | 113 | msg.function = do_delconn; |
mbed_official | 0:51ac1d130fd4 | 114 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 115 | tcpip_apimsg(&msg); |
mbed_official | 0:51ac1d130fd4 | 116 | |
mbed_official | 0:51ac1d130fd4 | 117 | netconn_free(conn); |
mbed_official | 0:51ac1d130fd4 | 118 | |
mbed_official | 0:51ac1d130fd4 | 119 | /* don't care for return value of do_delconn since it only calls void functions */ |
mbed_official | 0:51ac1d130fd4 | 120 | |
mbed_official | 0:51ac1d130fd4 | 121 | return ERR_OK; |
mbed_official | 0:51ac1d130fd4 | 122 | } |
mbed_official | 0:51ac1d130fd4 | 123 | |
mbed_official | 0:51ac1d130fd4 | 124 | /** |
mbed_official | 0:51ac1d130fd4 | 125 | * Get the local or remote IP address and port of a netconn. |
mbed_official | 0:51ac1d130fd4 | 126 | * For RAW netconns, this returns the protocol instead of a port! |
mbed_official | 0:51ac1d130fd4 | 127 | * |
mbed_official | 0:51ac1d130fd4 | 128 | * @param conn the netconn to query |
mbed_official | 0:51ac1d130fd4 | 129 | * @param addr a pointer to which to save the IP address |
mbed_official | 0:51ac1d130fd4 | 130 | * @param port a pointer to which to save the port (or protocol for RAW) |
mbed_official | 0:51ac1d130fd4 | 131 | * @param local 1 to get the local IP address, 0 to get the remote one |
mbed_official | 0:51ac1d130fd4 | 132 | * @return ERR_CONN for invalid connections |
mbed_official | 0:51ac1d130fd4 | 133 | * ERR_OK if the information was retrieved |
mbed_official | 0:51ac1d130fd4 | 134 | */ |
mbed_official | 0:51ac1d130fd4 | 135 | err_t |
mbed_official | 0:51ac1d130fd4 | 136 | netconn_getaddr(struct netconn *conn, ip_addr_t *addr, u16_t *port, u8_t local) |
mbed_official | 0:51ac1d130fd4 | 137 | { |
mbed_official | 0:51ac1d130fd4 | 138 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 139 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 140 | |
mbed_official | 0:51ac1d130fd4 | 141 | LWIP_ERROR("netconn_getaddr: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 142 | LWIP_ERROR("netconn_getaddr: invalid addr", (addr != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 143 | LWIP_ERROR("netconn_getaddr: invalid port", (port != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 144 | |
mbed_official | 0:51ac1d130fd4 | 145 | msg.function = do_getaddr; |
mbed_official | 0:51ac1d130fd4 | 146 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 147 | msg.msg.msg.ad.ipaddr = addr; |
mbed_official | 0:51ac1d130fd4 | 148 | msg.msg.msg.ad.port = port; |
mbed_official | 0:51ac1d130fd4 | 149 | msg.msg.msg.ad.local = local; |
mbed_official | 0:51ac1d130fd4 | 150 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 151 | |
mbed_official | 0:51ac1d130fd4 | 152 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 153 | return err; |
mbed_official | 0:51ac1d130fd4 | 154 | } |
mbed_official | 0:51ac1d130fd4 | 155 | |
mbed_official | 0:51ac1d130fd4 | 156 | /** |
mbed_official | 0:51ac1d130fd4 | 157 | * Bind a netconn to a specific local IP address and port. |
mbed_official | 0:51ac1d130fd4 | 158 | * Binding one netconn twice might not always be checked correctly! |
mbed_official | 0:51ac1d130fd4 | 159 | * |
mbed_official | 0:51ac1d130fd4 | 160 | * @param conn the netconn to bind |
mbed_official | 0:51ac1d130fd4 | 161 | * @param addr the local IP address to bind the netconn to (use IP_ADDR_ANY |
mbed_official | 0:51ac1d130fd4 | 162 | * to bind to all addresses) |
mbed_official | 0:51ac1d130fd4 | 163 | * @param port the local port to bind the netconn to (not used for RAW) |
mbed_official | 0:51ac1d130fd4 | 164 | * @return ERR_OK if bound, any other err_t on failure |
mbed_official | 0:51ac1d130fd4 | 165 | */ |
mbed_official | 0:51ac1d130fd4 | 166 | err_t |
mbed_official | 0:51ac1d130fd4 | 167 | netconn_bind(struct netconn *conn, ip_addr_t *addr, u16_t port) |
mbed_official | 0:51ac1d130fd4 | 168 | { |
mbed_official | 0:51ac1d130fd4 | 169 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 170 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 171 | |
mbed_official | 0:51ac1d130fd4 | 172 | LWIP_ERROR("netconn_bind: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 173 | |
mbed_official | 0:51ac1d130fd4 | 174 | msg.function = do_bind; |
mbed_official | 0:51ac1d130fd4 | 175 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 176 | msg.msg.msg.bc.ipaddr = addr; |
mbed_official | 0:51ac1d130fd4 | 177 | msg.msg.msg.bc.port = port; |
mbed_official | 0:51ac1d130fd4 | 178 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 179 | |
mbed_official | 0:51ac1d130fd4 | 180 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 181 | return err; |
mbed_official | 0:51ac1d130fd4 | 182 | } |
mbed_official | 0:51ac1d130fd4 | 183 | |
mbed_official | 0:51ac1d130fd4 | 184 | /** |
mbed_official | 0:51ac1d130fd4 | 185 | * Connect a netconn to a specific remote IP address and port. |
mbed_official | 0:51ac1d130fd4 | 186 | * |
mbed_official | 0:51ac1d130fd4 | 187 | * @param conn the netconn to connect |
mbed_official | 0:51ac1d130fd4 | 188 | * @param addr the remote IP address to connect to |
mbed_official | 0:51ac1d130fd4 | 189 | * @param port the remote port to connect to (no used for RAW) |
mbed_official | 0:51ac1d130fd4 | 190 | * @return ERR_OK if connected, return value of tcp_/udp_/raw_connect otherwise |
mbed_official | 0:51ac1d130fd4 | 191 | */ |
mbed_official | 0:51ac1d130fd4 | 192 | err_t |
mbed_official | 0:51ac1d130fd4 | 193 | netconn_connect(struct netconn *conn, ip_addr_t *addr, u16_t port) |
mbed_official | 0:51ac1d130fd4 | 194 | { |
mbed_official | 0:51ac1d130fd4 | 195 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 196 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 197 | |
mbed_official | 0:51ac1d130fd4 | 198 | LWIP_ERROR("netconn_connect: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 199 | msg.function = do_connect; |
mbed_official | 0:51ac1d130fd4 | 200 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 201 | msg.msg.msg.bc.ipaddr = addr; |
mbed_official | 0:51ac1d130fd4 | 202 | msg.msg.msg.bc.port = port; |
mbed_official | 0:51ac1d130fd4 | 203 | /* This is the only function which need to not block tcpip_thread */ |
mbed_official | 0:51ac1d130fd4 | 204 | err = tcpip_apimsg(&msg); |
rebonatto | 12:963887732b7c | 205 | if(err != 0) |
rebonatto | 12:963887732b7c | 206 | printf("Pau em tcpip_apimsg\n"); |
rebonatto | 12:963887732b7c | 207 | |
mbed_official | 0:51ac1d130fd4 | 208 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 209 | return err; |
mbed_official | 0:51ac1d130fd4 | 210 | } |
mbed_official | 0:51ac1d130fd4 | 211 | |
mbed_official | 0:51ac1d130fd4 | 212 | /** |
mbed_official | 0:51ac1d130fd4 | 213 | * Disconnect a netconn from its current peer (only valid for UDP netconns). |
mbed_official | 0:51ac1d130fd4 | 214 | * |
mbed_official | 0:51ac1d130fd4 | 215 | * @param conn the netconn to disconnect |
mbed_official | 0:51ac1d130fd4 | 216 | * @return TODO: return value is not set here... |
mbed_official | 0:51ac1d130fd4 | 217 | */ |
mbed_official | 0:51ac1d130fd4 | 218 | err_t |
mbed_official | 0:51ac1d130fd4 | 219 | netconn_disconnect(struct netconn *conn) |
mbed_official | 0:51ac1d130fd4 | 220 | { |
mbed_official | 0:51ac1d130fd4 | 221 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 222 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 223 | |
mbed_official | 0:51ac1d130fd4 | 224 | LWIP_ERROR("netconn_disconnect: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 225 | |
mbed_official | 0:51ac1d130fd4 | 226 | msg.function = do_disconnect; |
mbed_official | 0:51ac1d130fd4 | 227 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 228 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 229 | |
mbed_official | 0:51ac1d130fd4 | 230 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 231 | return err; |
mbed_official | 0:51ac1d130fd4 | 232 | } |
mbed_official | 0:51ac1d130fd4 | 233 | |
mbed_official | 0:51ac1d130fd4 | 234 | /** |
mbed_official | 0:51ac1d130fd4 | 235 | * Set a TCP netconn into listen mode |
mbed_official | 0:51ac1d130fd4 | 236 | * |
mbed_official | 0:51ac1d130fd4 | 237 | * @param conn the tcp netconn to set to listen mode |
mbed_official | 0:51ac1d130fd4 | 238 | * @param backlog the listen backlog, only used if TCP_LISTEN_BACKLOG==1 |
mbed_official | 0:51ac1d130fd4 | 239 | * @return ERR_OK if the netconn was set to listen (UDP and RAW netconns |
mbed_official | 0:51ac1d130fd4 | 240 | * don't return any error (yet?)) |
mbed_official | 0:51ac1d130fd4 | 241 | */ |
mbed_official | 0:51ac1d130fd4 | 242 | err_t |
mbed_official | 0:51ac1d130fd4 | 243 | netconn_listen_with_backlog(struct netconn *conn, u8_t backlog) |
mbed_official | 0:51ac1d130fd4 | 244 | { |
mbed_official | 0:51ac1d130fd4 | 245 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 246 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 247 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 248 | |
mbed_official | 0:51ac1d130fd4 | 249 | /* This does no harm. If TCP_LISTEN_BACKLOG is off, backlog is unused. */ |
mbed_official | 0:51ac1d130fd4 | 250 | LWIP_UNUSED_ARG(backlog); |
mbed_official | 0:51ac1d130fd4 | 251 | |
mbed_official | 0:51ac1d130fd4 | 252 | LWIP_ERROR("netconn_listen: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 253 | |
mbed_official | 0:51ac1d130fd4 | 254 | msg.function = do_listen; |
mbed_official | 0:51ac1d130fd4 | 255 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 256 | #if TCP_LISTEN_BACKLOG |
mbed_official | 0:51ac1d130fd4 | 257 | msg.msg.msg.lb.backlog = backlog; |
mbed_official | 0:51ac1d130fd4 | 258 | #endif /* TCP_LISTEN_BACKLOG */ |
mbed_official | 0:51ac1d130fd4 | 259 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 260 | |
mbed_official | 0:51ac1d130fd4 | 261 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 262 | return err; |
mbed_official | 0:51ac1d130fd4 | 263 | #else /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 264 | LWIP_UNUSED_ARG(conn); |
mbed_official | 0:51ac1d130fd4 | 265 | LWIP_UNUSED_ARG(backlog); |
mbed_official | 0:51ac1d130fd4 | 266 | return ERR_ARG; |
mbed_official | 0:51ac1d130fd4 | 267 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 268 | } |
mbed_official | 0:51ac1d130fd4 | 269 | |
mbed_official | 0:51ac1d130fd4 | 270 | /** |
mbed_official | 0:51ac1d130fd4 | 271 | * Accept a new connection on a TCP listening netconn. |
mbed_official | 0:51ac1d130fd4 | 272 | * |
mbed_official | 0:51ac1d130fd4 | 273 | * @param conn the TCP listen netconn |
mbed_official | 0:51ac1d130fd4 | 274 | * @param new_conn pointer where the new connection is stored |
mbed_official | 0:51ac1d130fd4 | 275 | * @return ERR_OK if a new connection has been received or an error |
mbed_official | 0:51ac1d130fd4 | 276 | * code otherwise |
mbed_official | 0:51ac1d130fd4 | 277 | */ |
mbed_official | 0:51ac1d130fd4 | 278 | err_t |
mbed_official | 0:51ac1d130fd4 | 279 | netconn_accept(struct netconn *conn, struct netconn **new_conn) |
mbed_official | 0:51ac1d130fd4 | 280 | { |
mbed_official | 0:51ac1d130fd4 | 281 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 282 | struct netconn *newconn; |
mbed_official | 0:51ac1d130fd4 | 283 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 284 | #if TCP_LISTEN_BACKLOG |
mbed_official | 0:51ac1d130fd4 | 285 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 286 | #endif /* TCP_LISTEN_BACKLOG */ |
mbed_official | 0:51ac1d130fd4 | 287 | |
mbed_official | 0:51ac1d130fd4 | 288 | LWIP_ERROR("netconn_accept: invalid pointer", (new_conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 289 | *new_conn = NULL; |
mbed_official | 0:51ac1d130fd4 | 290 | LWIP_ERROR("netconn_accept: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 291 | LWIP_ERROR("netconn_accept: invalid acceptmbox", sys_mbox_valid(&conn->acceptmbox), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 292 | |
mbed_official | 0:51ac1d130fd4 | 293 | err = conn->last_err; |
mbed_official | 0:51ac1d130fd4 | 294 | if (ERR_IS_FATAL(err)) { |
mbed_official | 0:51ac1d130fd4 | 295 | /* don't recv on fatal errors: this might block the application task |
mbed_official | 0:51ac1d130fd4 | 296 | waiting on acceptmbox forever! */ |
mbed_official | 0:51ac1d130fd4 | 297 | return err; |
mbed_official | 0:51ac1d130fd4 | 298 | } |
mbed_official | 0:51ac1d130fd4 | 299 | |
mbed_official | 0:51ac1d130fd4 | 300 | #if LWIP_SO_RCVTIMEO |
mbed_official | 0:51ac1d130fd4 | 301 | if (sys_arch_mbox_fetch(&conn->acceptmbox, (void **)&newconn, conn->recv_timeout) == SYS_ARCH_TIMEOUT) { |
mbed_official | 0:51ac1d130fd4 | 302 | NETCONN_SET_SAFE_ERR(conn, ERR_TIMEOUT); |
mbed_official | 0:51ac1d130fd4 | 303 | return ERR_TIMEOUT; |
mbed_official | 0:51ac1d130fd4 | 304 | } |
mbed_official | 0:51ac1d130fd4 | 305 | #else |
mbed_official | 0:51ac1d130fd4 | 306 | sys_arch_mbox_fetch(&conn->acceptmbox, (void **)&newconn, 0); |
mbed_official | 0:51ac1d130fd4 | 307 | #endif /* LWIP_SO_RCVTIMEO*/ |
mbed_official | 0:51ac1d130fd4 | 308 | /* Register event with callback */ |
mbed_official | 0:51ac1d130fd4 | 309 | API_EVENT(conn, NETCONN_EVT_RCVMINUS, 0); |
mbed_official | 0:51ac1d130fd4 | 310 | |
mbed_official | 0:51ac1d130fd4 | 311 | if (newconn == NULL) { |
mbed_official | 0:51ac1d130fd4 | 312 | /* connection has been aborted */ |
mbed_official | 0:51ac1d130fd4 | 313 | NETCONN_SET_SAFE_ERR(conn, ERR_ABRT); |
mbed_official | 0:51ac1d130fd4 | 314 | return ERR_ABRT; |
mbed_official | 0:51ac1d130fd4 | 315 | } |
mbed_official | 0:51ac1d130fd4 | 316 | #if TCP_LISTEN_BACKLOG |
mbed_official | 0:51ac1d130fd4 | 317 | /* Let the stack know that we have accepted the connection. */ |
mbed_official | 0:51ac1d130fd4 | 318 | msg.function = do_recv; |
mbed_official | 0:51ac1d130fd4 | 319 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 320 | /* don't care for the return value of do_recv */ |
mbed_official | 0:51ac1d130fd4 | 321 | TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 322 | #endif /* TCP_LISTEN_BACKLOG */ |
mbed_official | 0:51ac1d130fd4 | 323 | |
mbed_official | 0:51ac1d130fd4 | 324 | *new_conn = newconn; |
mbed_official | 0:51ac1d130fd4 | 325 | /* don't set conn->last_err: it's only ERR_OK, anyway */ |
mbed_official | 0:51ac1d130fd4 | 326 | return ERR_OK; |
mbed_official | 0:51ac1d130fd4 | 327 | #else /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 328 | LWIP_UNUSED_ARG(conn); |
mbed_official | 0:51ac1d130fd4 | 329 | LWIP_UNUSED_ARG(new_conn); |
mbed_official | 0:51ac1d130fd4 | 330 | return ERR_ARG; |
mbed_official | 0:51ac1d130fd4 | 331 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 332 | } |
mbed_official | 0:51ac1d130fd4 | 333 | |
mbed_official | 0:51ac1d130fd4 | 334 | /** |
mbed_official | 0:51ac1d130fd4 | 335 | * Receive data: actual implementation that doesn't care whether pbuf or netbuf |
mbed_official | 0:51ac1d130fd4 | 336 | * is received |
mbed_official | 0:51ac1d130fd4 | 337 | * |
mbed_official | 0:51ac1d130fd4 | 338 | * @param conn the netconn from which to receive data |
mbed_official | 0:51ac1d130fd4 | 339 | * @param new_buf pointer where a new pbuf/netbuf is stored when received data |
mbed_official | 0:51ac1d130fd4 | 340 | * @return ERR_OK if data has been received, an error code otherwise (timeout, |
mbed_official | 0:51ac1d130fd4 | 341 | * memory error or another error) |
mbed_official | 0:51ac1d130fd4 | 342 | */ |
mbed_official | 0:51ac1d130fd4 | 343 | static err_t |
mbed_official | 0:51ac1d130fd4 | 344 | netconn_recv_data(struct netconn *conn, void **new_buf) |
mbed_official | 0:51ac1d130fd4 | 345 | { |
mbed_official | 0:51ac1d130fd4 | 346 | void *buf = NULL; |
mbed_official | 0:51ac1d130fd4 | 347 | u16_t len; |
mbed_official | 0:51ac1d130fd4 | 348 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 349 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 350 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 351 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 352 | |
mbed_official | 0:51ac1d130fd4 | 353 | LWIP_ERROR("netconn_recv: invalid pointer", (new_buf != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 354 | *new_buf = NULL; |
mbed_official | 0:51ac1d130fd4 | 355 | LWIP_ERROR("netconn_recv: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 356 | LWIP_ERROR("netconn_accept: invalid recvmbox", sys_mbox_valid(&conn->recvmbox), return ERR_CONN;); |
mbed_official | 0:51ac1d130fd4 | 357 | |
mbed_official | 0:51ac1d130fd4 | 358 | err = conn->last_err; |
mbed_official | 0:51ac1d130fd4 | 359 | if (ERR_IS_FATAL(err)) { |
mbed_official | 0:51ac1d130fd4 | 360 | /* don't recv on fatal errors: this might block the application task |
mbed_official | 0:51ac1d130fd4 | 361 | waiting on recvmbox forever! */ |
mbed_official | 0:51ac1d130fd4 | 362 | /* @todo: this does not allow us to fetch data that has been put into recvmbox |
mbed_official | 0:51ac1d130fd4 | 363 | before the fatal error occurred - is that a problem? */ |
mbed_official | 0:51ac1d130fd4 | 364 | return err; |
mbed_official | 0:51ac1d130fd4 | 365 | } |
mbed_official | 0:51ac1d130fd4 | 366 | |
mbed_official | 0:51ac1d130fd4 | 367 | #if LWIP_SO_RCVTIMEO |
mbed_official | 0:51ac1d130fd4 | 368 | if (sys_arch_mbox_fetch(&conn->recvmbox, &buf, conn->recv_timeout) == SYS_ARCH_TIMEOUT) { |
mbed_official | 0:51ac1d130fd4 | 369 | NETCONN_SET_SAFE_ERR(conn, ERR_TIMEOUT); |
mbed_official | 0:51ac1d130fd4 | 370 | return ERR_TIMEOUT; |
mbed_official | 0:51ac1d130fd4 | 371 | } |
mbed_official | 0:51ac1d130fd4 | 372 | #else |
mbed_official | 0:51ac1d130fd4 | 373 | sys_arch_mbox_fetch(&conn->recvmbox, &buf, 0); |
mbed_official | 0:51ac1d130fd4 | 374 | #endif /* LWIP_SO_RCVTIMEO*/ |
mbed_official | 0:51ac1d130fd4 | 375 | |
mbed_official | 0:51ac1d130fd4 | 376 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 377 | if (conn->type == NETCONN_TCP) { |
mbed_official | 0:51ac1d130fd4 | 378 | if (!netconn_get_noautorecved(conn) || (buf == NULL)) { |
mbed_official | 0:51ac1d130fd4 | 379 | /* Let the stack know that we have taken the data. */ |
mbed_official | 0:51ac1d130fd4 | 380 | /* TODO: Speedup: Don't block and wait for the answer here |
mbed_official | 0:51ac1d130fd4 | 381 | (to prevent multiple thread-switches). */ |
mbed_official | 0:51ac1d130fd4 | 382 | msg.function = do_recv; |
mbed_official | 0:51ac1d130fd4 | 383 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 384 | if (buf != NULL) { |
mbed_official | 0:51ac1d130fd4 | 385 | msg.msg.msg.r.len = ((struct pbuf *)buf)->tot_len; |
mbed_official | 0:51ac1d130fd4 | 386 | } else { |
mbed_official | 0:51ac1d130fd4 | 387 | msg.msg.msg.r.len = 1; |
mbed_official | 0:51ac1d130fd4 | 388 | } |
mbed_official | 0:51ac1d130fd4 | 389 | /* don't care for the return value of do_recv */ |
mbed_official | 0:51ac1d130fd4 | 390 | TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 391 | } |
mbed_official | 0:51ac1d130fd4 | 392 | |
mbed_official | 0:51ac1d130fd4 | 393 | /* If we are closed, we indicate that we no longer wish to use the socket */ |
mbed_official | 0:51ac1d130fd4 | 394 | if (buf == NULL) { |
mbed_official | 0:51ac1d130fd4 | 395 | API_EVENT(conn, NETCONN_EVT_RCVMINUS, 0); |
mbed_official | 0:51ac1d130fd4 | 396 | /* Avoid to lose any previous error code */ |
mbed_official | 0:51ac1d130fd4 | 397 | NETCONN_SET_SAFE_ERR(conn, ERR_CLSD); |
mbed_official | 0:51ac1d130fd4 | 398 | return ERR_CLSD; |
mbed_official | 0:51ac1d130fd4 | 399 | } |
mbed_official | 0:51ac1d130fd4 | 400 | len = ((struct pbuf *)buf)->tot_len; |
mbed_official | 0:51ac1d130fd4 | 401 | } |
mbed_official | 0:51ac1d130fd4 | 402 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 403 | #if LWIP_TCP && (LWIP_UDP || LWIP_RAW) |
mbed_official | 0:51ac1d130fd4 | 404 | else |
mbed_official | 0:51ac1d130fd4 | 405 | #endif /* LWIP_TCP && (LWIP_UDP || LWIP_RAW) */ |
mbed_official | 0:51ac1d130fd4 | 406 | #if (LWIP_UDP || LWIP_RAW) |
mbed_official | 0:51ac1d130fd4 | 407 | { |
mbed_official | 0:51ac1d130fd4 | 408 | LWIP_ASSERT("buf != NULL", buf != NULL); |
mbed_official | 0:51ac1d130fd4 | 409 | len = netbuf_len((struct netbuf *)buf); |
mbed_official | 0:51ac1d130fd4 | 410 | } |
mbed_official | 0:51ac1d130fd4 | 411 | #endif /* (LWIP_UDP || LWIP_RAW) */ |
mbed_official | 0:51ac1d130fd4 | 412 | |
mbed_official | 0:51ac1d130fd4 | 413 | #if LWIP_SO_RCVBUF |
mbed_official | 0:51ac1d130fd4 | 414 | SYS_ARCH_DEC(conn->recv_avail, len); |
mbed_official | 0:51ac1d130fd4 | 415 | #endif /* LWIP_SO_RCVBUF */ |
mbed_official | 0:51ac1d130fd4 | 416 | /* Register event with callback */ |
mbed_official | 0:51ac1d130fd4 | 417 | API_EVENT(conn, NETCONN_EVT_RCVMINUS, len); |
mbed_official | 0:51ac1d130fd4 | 418 | |
mbed_official | 0:51ac1d130fd4 | 419 | LWIP_DEBUGF(API_LIB_DEBUG, ("netconn_recv_data: received %p, len=%"U16_F"\n", buf, len)); |
mbed_official | 0:51ac1d130fd4 | 420 | |
mbed_official | 0:51ac1d130fd4 | 421 | *new_buf = buf; |
mbed_official | 0:51ac1d130fd4 | 422 | /* don't set conn->last_err: it's only ERR_OK, anyway */ |
mbed_official | 0:51ac1d130fd4 | 423 | return ERR_OK; |
mbed_official | 0:51ac1d130fd4 | 424 | } |
mbed_official | 0:51ac1d130fd4 | 425 | |
mbed_official | 0:51ac1d130fd4 | 426 | /** |
mbed_official | 0:51ac1d130fd4 | 427 | * Receive data (in form of a pbuf) from a TCP netconn |
mbed_official | 0:51ac1d130fd4 | 428 | * |
mbed_official | 0:51ac1d130fd4 | 429 | * @param conn the netconn from which to receive data |
mbed_official | 0:51ac1d130fd4 | 430 | * @param new_buf pointer where a new pbuf is stored when received data |
mbed_official | 0:51ac1d130fd4 | 431 | * @return ERR_OK if data has been received, an error code otherwise (timeout, |
mbed_official | 0:51ac1d130fd4 | 432 | * memory error or another error) |
mbed_official | 0:51ac1d130fd4 | 433 | * ERR_ARG if conn is not a TCP netconn |
mbed_official | 0:51ac1d130fd4 | 434 | */ |
mbed_official | 0:51ac1d130fd4 | 435 | err_t |
mbed_official | 0:51ac1d130fd4 | 436 | netconn_recv_tcp_pbuf(struct netconn *conn, struct pbuf **new_buf) |
mbed_official | 0:51ac1d130fd4 | 437 | { |
mbed_official | 0:51ac1d130fd4 | 438 | LWIP_ERROR("netconn_recv: invalid conn", (conn != NULL) && |
mbed_official | 0:51ac1d130fd4 | 439 | netconn_type(conn) == NETCONN_TCP, return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 440 | |
mbed_official | 0:51ac1d130fd4 | 441 | return netconn_recv_data(conn, (void **)new_buf); |
mbed_official | 0:51ac1d130fd4 | 442 | } |
mbed_official | 0:51ac1d130fd4 | 443 | |
mbed_official | 0:51ac1d130fd4 | 444 | /** |
mbed_official | 0:51ac1d130fd4 | 445 | * Receive data (in form of a netbuf containing a packet buffer) from a netconn |
mbed_official | 0:51ac1d130fd4 | 446 | * |
mbed_official | 0:51ac1d130fd4 | 447 | * @param conn the netconn from which to receive data |
mbed_official | 0:51ac1d130fd4 | 448 | * @param new_buf pointer where a new netbuf is stored when received data |
mbed_official | 0:51ac1d130fd4 | 449 | * @return ERR_OK if data has been received, an error code otherwise (timeout, |
mbed_official | 0:51ac1d130fd4 | 450 | * memory error or another error) |
mbed_official | 0:51ac1d130fd4 | 451 | */ |
mbed_official | 0:51ac1d130fd4 | 452 | err_t |
mbed_official | 0:51ac1d130fd4 | 453 | netconn_recv(struct netconn *conn, struct netbuf **new_buf) |
mbed_official | 0:51ac1d130fd4 | 454 | { |
mbed_official | 0:51ac1d130fd4 | 455 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 456 | struct netbuf *buf = NULL; |
mbed_official | 0:51ac1d130fd4 | 457 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 458 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 459 | |
mbed_official | 0:51ac1d130fd4 | 460 | LWIP_ERROR("netconn_recv: invalid pointer", (new_buf != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 461 | *new_buf = NULL; |
mbed_official | 0:51ac1d130fd4 | 462 | LWIP_ERROR("netconn_recv: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 463 | LWIP_ERROR("netconn_accept: invalid recvmbox", sys_mbox_valid(&conn->recvmbox), return ERR_CONN;); |
mbed_official | 0:51ac1d130fd4 | 464 | |
mbed_official | 0:51ac1d130fd4 | 465 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 466 | if (conn->type == NETCONN_TCP) { |
mbed_official | 0:51ac1d130fd4 | 467 | struct pbuf *p = NULL; |
mbed_official | 0:51ac1d130fd4 | 468 | /* This is not a listening netconn, since recvmbox is set */ |
mbed_official | 0:51ac1d130fd4 | 469 | |
mbed_official | 0:51ac1d130fd4 | 470 | buf = (struct netbuf *)memp_malloc(MEMP_NETBUF); |
mbed_official | 0:51ac1d130fd4 | 471 | if (buf == NULL) { |
mbed_official | 0:51ac1d130fd4 | 472 | NETCONN_SET_SAFE_ERR(conn, ERR_MEM); |
mbed_official | 0:51ac1d130fd4 | 473 | return ERR_MEM; |
mbed_official | 0:51ac1d130fd4 | 474 | } |
mbed_official | 0:51ac1d130fd4 | 475 | |
mbed_official | 0:51ac1d130fd4 | 476 | err = netconn_recv_data(conn, (void **)&p); |
mbed_official | 0:51ac1d130fd4 | 477 | if (err != ERR_OK) { |
mbed_official | 0:51ac1d130fd4 | 478 | memp_free(MEMP_NETBUF, buf); |
mbed_official | 0:51ac1d130fd4 | 479 | return err; |
mbed_official | 0:51ac1d130fd4 | 480 | } |
mbed_official | 0:51ac1d130fd4 | 481 | LWIP_ASSERT("p != NULL", p != NULL); |
mbed_official | 0:51ac1d130fd4 | 482 | |
mbed_official | 0:51ac1d130fd4 | 483 | buf->p = p; |
mbed_official | 0:51ac1d130fd4 | 484 | buf->ptr = p; |
mbed_official | 0:51ac1d130fd4 | 485 | buf->port = 0; |
mbed_official | 0:51ac1d130fd4 | 486 | ip_addr_set_any(&buf->addr); |
mbed_official | 0:51ac1d130fd4 | 487 | *new_buf = buf; |
mbed_official | 0:51ac1d130fd4 | 488 | /* don't set conn->last_err: it's only ERR_OK, anyway */ |
mbed_official | 0:51ac1d130fd4 | 489 | return ERR_OK; |
mbed_official | 0:51ac1d130fd4 | 490 | } else |
mbed_official | 0:51ac1d130fd4 | 491 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 492 | { |
mbed_official | 0:51ac1d130fd4 | 493 | #if (LWIP_UDP || LWIP_RAW) |
mbed_official | 0:51ac1d130fd4 | 494 | return netconn_recv_data(conn, (void **)new_buf); |
mbed_official | 0:51ac1d130fd4 | 495 | #endif /* (LWIP_UDP || LWIP_RAW) */ |
mbed_official | 0:51ac1d130fd4 | 496 | } |
mbed_official | 0:51ac1d130fd4 | 497 | } |
mbed_official | 0:51ac1d130fd4 | 498 | |
mbed_official | 0:51ac1d130fd4 | 499 | /** |
mbed_official | 0:51ac1d130fd4 | 500 | * TCP: update the receive window: by calling this, the application |
mbed_official | 0:51ac1d130fd4 | 501 | * tells the stack that it has processed data and is able to accept |
mbed_official | 0:51ac1d130fd4 | 502 | * new data. |
mbed_official | 0:51ac1d130fd4 | 503 | * ATTENTION: use with care, this is mainly used for sockets! |
mbed_official | 0:51ac1d130fd4 | 504 | * Can only be used when calling netconn_set_noautorecved(conn, 1) before. |
mbed_official | 0:51ac1d130fd4 | 505 | * |
mbed_official | 0:51ac1d130fd4 | 506 | * @param conn the netconn for which to update the receive window |
mbed_official | 0:51ac1d130fd4 | 507 | * @param length amount of data processed (ATTENTION: this must be accurate!) |
mbed_official | 0:51ac1d130fd4 | 508 | */ |
mbed_official | 0:51ac1d130fd4 | 509 | void |
mbed_official | 0:51ac1d130fd4 | 510 | netconn_recved(struct netconn *conn, u32_t length) |
mbed_official | 0:51ac1d130fd4 | 511 | { |
mbed_official | 0:51ac1d130fd4 | 512 | #if LWIP_TCP |
mbed_official | 0:51ac1d130fd4 | 513 | if ((conn != NULL) && (conn->type == NETCONN_TCP) && |
mbed_official | 0:51ac1d130fd4 | 514 | (netconn_get_noautorecved(conn))) { |
mbed_official | 0:51ac1d130fd4 | 515 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 516 | /* Let the stack know that we have taken the data. */ |
mbed_official | 0:51ac1d130fd4 | 517 | /* TODO: Speedup: Don't block and wait for the answer here |
mbed_official | 0:51ac1d130fd4 | 518 | (to prevent multiple thread-switches). */ |
mbed_official | 0:51ac1d130fd4 | 519 | msg.function = do_recv; |
mbed_official | 0:51ac1d130fd4 | 520 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 521 | msg.msg.msg.r.len = length; |
mbed_official | 0:51ac1d130fd4 | 522 | /* don't care for the return value of do_recv */ |
mbed_official | 0:51ac1d130fd4 | 523 | TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 524 | } |
mbed_official | 0:51ac1d130fd4 | 525 | #else /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 526 | LWIP_UNUSED_ARG(conn); |
mbed_official | 0:51ac1d130fd4 | 527 | LWIP_UNUSED_ARG(length); |
mbed_official | 0:51ac1d130fd4 | 528 | #endif /* LWIP_TCP */ |
mbed_official | 0:51ac1d130fd4 | 529 | } |
mbed_official | 0:51ac1d130fd4 | 530 | |
mbed_official | 0:51ac1d130fd4 | 531 | /** |
mbed_official | 0:51ac1d130fd4 | 532 | * Send data (in form of a netbuf) to a specific remote IP address and port. |
mbed_official | 0:51ac1d130fd4 | 533 | * Only to be used for UDP and RAW netconns (not TCP). |
mbed_official | 0:51ac1d130fd4 | 534 | * |
mbed_official | 0:51ac1d130fd4 | 535 | * @param conn the netconn over which to send data |
mbed_official | 0:51ac1d130fd4 | 536 | * @param buf a netbuf containing the data to send |
mbed_official | 0:51ac1d130fd4 | 537 | * @param addr the remote IP address to which to send the data |
mbed_official | 0:51ac1d130fd4 | 538 | * @param port the remote port to which to send the data |
mbed_official | 0:51ac1d130fd4 | 539 | * @return ERR_OK if data was sent, any other err_t on error |
mbed_official | 0:51ac1d130fd4 | 540 | */ |
mbed_official | 0:51ac1d130fd4 | 541 | err_t |
mbed_official | 0:51ac1d130fd4 | 542 | netconn_sendto(struct netconn *conn, struct netbuf *buf, ip_addr_t *addr, u16_t port) |
mbed_official | 0:51ac1d130fd4 | 543 | { |
mbed_official | 0:51ac1d130fd4 | 544 | if (buf != NULL) { |
mbed_official | 0:51ac1d130fd4 | 545 | ip_addr_set(&buf->addr, addr); |
mbed_official | 0:51ac1d130fd4 | 546 | buf->port = port; |
mbed_official | 0:51ac1d130fd4 | 547 | return netconn_send(conn, buf); |
mbed_official | 0:51ac1d130fd4 | 548 | } |
mbed_official | 0:51ac1d130fd4 | 549 | return ERR_VAL; |
mbed_official | 0:51ac1d130fd4 | 550 | } |
mbed_official | 0:51ac1d130fd4 | 551 | |
mbed_official | 0:51ac1d130fd4 | 552 | /** |
mbed_official | 0:51ac1d130fd4 | 553 | * Send data over a UDP or RAW netconn (that is already connected). |
mbed_official | 0:51ac1d130fd4 | 554 | * |
mbed_official | 0:51ac1d130fd4 | 555 | * @param conn the UDP or RAW netconn over which to send data |
mbed_official | 0:51ac1d130fd4 | 556 | * @param buf a netbuf containing the data to send |
mbed_official | 0:51ac1d130fd4 | 557 | * @return ERR_OK if data was sent, any other err_t on error |
mbed_official | 0:51ac1d130fd4 | 558 | */ |
mbed_official | 0:51ac1d130fd4 | 559 | err_t |
mbed_official | 0:51ac1d130fd4 | 560 | netconn_send(struct netconn *conn, struct netbuf *buf) |
mbed_official | 0:51ac1d130fd4 | 561 | { |
mbed_official | 0:51ac1d130fd4 | 562 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 563 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 564 | |
mbed_official | 0:51ac1d130fd4 | 565 | LWIP_ERROR("netconn_send: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 566 | |
mbed_official | 0:51ac1d130fd4 | 567 | LWIP_DEBUGF(API_LIB_DEBUG, ("netconn_send: sending %"U16_F" bytes\n", buf->p->tot_len)); |
mbed_official | 0:51ac1d130fd4 | 568 | msg.function = do_send; |
mbed_official | 0:51ac1d130fd4 | 569 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 570 | msg.msg.msg.b = buf; |
mbed_official | 0:51ac1d130fd4 | 571 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 572 | |
mbed_official | 0:51ac1d130fd4 | 573 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 574 | return err; |
mbed_official | 0:51ac1d130fd4 | 575 | } |
mbed_official | 0:51ac1d130fd4 | 576 | |
mbed_official | 0:51ac1d130fd4 | 577 | /** |
mbed_official | 0:51ac1d130fd4 | 578 | * Send data over a TCP netconn. |
mbed_official | 0:51ac1d130fd4 | 579 | * |
mbed_official | 0:51ac1d130fd4 | 580 | * @param conn the TCP netconn over which to send data |
mbed_official | 0:51ac1d130fd4 | 581 | * @param dataptr pointer to the application buffer that contains the data to send |
mbed_official | 0:51ac1d130fd4 | 582 | * @param size size of the application data to send |
mbed_official | 0:51ac1d130fd4 | 583 | * @param apiflags combination of following flags : |
mbed_official | 0:51ac1d130fd4 | 584 | * - NETCONN_COPY: data will be copied into memory belonging to the stack |
mbed_official | 0:51ac1d130fd4 | 585 | * - NETCONN_MORE: for TCP connection, PSH flag will be set on last segment sent |
mbed_official | 0:51ac1d130fd4 | 586 | * - NETCONN_DONTBLOCK: only write the data if all dat can be written at once |
mbed_official | 0:51ac1d130fd4 | 587 | * @return ERR_OK if data was sent, any other err_t on error |
mbed_official | 0:51ac1d130fd4 | 588 | */ |
mbed_official | 0:51ac1d130fd4 | 589 | err_t |
mbed_official | 0:51ac1d130fd4 | 590 | netconn_write(struct netconn *conn, const void *dataptr, size_t size, u8_t apiflags) |
mbed_official | 0:51ac1d130fd4 | 591 | { |
mbed_official | 0:51ac1d130fd4 | 592 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 593 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 594 | |
mbed_official | 0:51ac1d130fd4 | 595 | LWIP_ERROR("netconn_write: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 596 | LWIP_ERROR("netconn_write: invalid conn->type", (conn->type == NETCONN_TCP), return ERR_VAL;); |
mbed_official | 0:51ac1d130fd4 | 597 | if (size == 0) { |
mbed_official | 0:51ac1d130fd4 | 598 | return ERR_OK; |
mbed_official | 0:51ac1d130fd4 | 599 | } |
mbed_official | 0:51ac1d130fd4 | 600 | |
mbed_official | 0:51ac1d130fd4 | 601 | /* @todo: for non-blocking write, check if 'size' would ever fit into |
mbed_official | 0:51ac1d130fd4 | 602 | snd_queue or snd_buf */ |
mbed_official | 0:51ac1d130fd4 | 603 | msg.function = do_write; |
mbed_official | 0:51ac1d130fd4 | 604 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 605 | msg.msg.msg.w.dataptr = dataptr; |
mbed_official | 0:51ac1d130fd4 | 606 | msg.msg.msg.w.apiflags = apiflags; |
mbed_official | 0:51ac1d130fd4 | 607 | msg.msg.msg.w.len = size; |
mbed_official | 0:51ac1d130fd4 | 608 | /* For locking the core: this _can_ be delayed on low memory/low send buffer, |
mbed_official | 0:51ac1d130fd4 | 609 | but if it is, this is done inside api_msg.c:do_write(), so we can use the |
mbed_official | 0:51ac1d130fd4 | 610 | non-blocking version here. */ |
mbed_official | 0:51ac1d130fd4 | 611 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 612 | |
mbed_official | 0:51ac1d130fd4 | 613 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 614 | return err; |
mbed_official | 0:51ac1d130fd4 | 615 | } |
mbed_official | 0:51ac1d130fd4 | 616 | |
mbed_official | 0:51ac1d130fd4 | 617 | /** |
mbed_official | 0:51ac1d130fd4 | 618 | * Close ot shutdown a TCP netconn (doesn't delete it). |
mbed_official | 0:51ac1d130fd4 | 619 | * |
mbed_official | 0:51ac1d130fd4 | 620 | * @param conn the TCP netconn to close or shutdown |
mbed_official | 0:51ac1d130fd4 | 621 | * @param how fully close or only shutdown one side? |
mbed_official | 0:51ac1d130fd4 | 622 | * @return ERR_OK if the netconn was closed, any other err_t on error |
mbed_official | 0:51ac1d130fd4 | 623 | */ |
mbed_official | 0:51ac1d130fd4 | 624 | static err_t |
mbed_official | 0:51ac1d130fd4 | 625 | netconn_close_shutdown(struct netconn *conn, u8_t how) |
mbed_official | 0:51ac1d130fd4 | 626 | { |
mbed_official | 0:51ac1d130fd4 | 627 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 628 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 629 | |
mbed_official | 0:51ac1d130fd4 | 630 | LWIP_ERROR("netconn_close: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 631 | |
mbed_official | 0:51ac1d130fd4 | 632 | msg.function = do_close; |
mbed_official | 0:51ac1d130fd4 | 633 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 634 | /* shutting down both ends is the same as closing */ |
mbed_official | 0:51ac1d130fd4 | 635 | msg.msg.msg.sd.shut = how; |
mbed_official | 0:51ac1d130fd4 | 636 | /* because of the LWIP_TCPIP_CORE_LOCKING implementation of do_close, |
mbed_official | 0:51ac1d130fd4 | 637 | don't use TCPIP_APIMSG here */ |
mbed_official | 0:51ac1d130fd4 | 638 | err = tcpip_apimsg(&msg); |
mbed_official | 0:51ac1d130fd4 | 639 | |
mbed_official | 0:51ac1d130fd4 | 640 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 641 | return err; |
mbed_official | 0:51ac1d130fd4 | 642 | } |
mbed_official | 0:51ac1d130fd4 | 643 | |
mbed_official | 0:51ac1d130fd4 | 644 | /** |
mbed_official | 0:51ac1d130fd4 | 645 | * Close a TCP netconn (doesn't delete it). |
mbed_official | 0:51ac1d130fd4 | 646 | * |
mbed_official | 0:51ac1d130fd4 | 647 | * @param conn the TCP netconn to close |
mbed_official | 0:51ac1d130fd4 | 648 | * @return ERR_OK if the netconn was closed, any other err_t on error |
mbed_official | 0:51ac1d130fd4 | 649 | */ |
mbed_official | 0:51ac1d130fd4 | 650 | err_t |
mbed_official | 0:51ac1d130fd4 | 651 | netconn_close(struct netconn *conn) |
mbed_official | 0:51ac1d130fd4 | 652 | { |
mbed_official | 0:51ac1d130fd4 | 653 | /* shutting down both ends is the same as closing */ |
mbed_official | 0:51ac1d130fd4 | 654 | return netconn_close_shutdown(conn, NETCONN_SHUT_RDWR); |
mbed_official | 0:51ac1d130fd4 | 655 | } |
mbed_official | 0:51ac1d130fd4 | 656 | |
mbed_official | 0:51ac1d130fd4 | 657 | /** |
mbed_official | 0:51ac1d130fd4 | 658 | * Shut down one or both sides of a TCP netconn (doesn't delete it). |
mbed_official | 0:51ac1d130fd4 | 659 | * |
mbed_official | 0:51ac1d130fd4 | 660 | * @param conn the TCP netconn to shut down |
mbed_official | 0:51ac1d130fd4 | 661 | * @return ERR_OK if the netconn was closed, any other err_t on error |
mbed_official | 0:51ac1d130fd4 | 662 | */ |
mbed_official | 0:51ac1d130fd4 | 663 | err_t |
mbed_official | 0:51ac1d130fd4 | 664 | netconn_shutdown(struct netconn *conn, u8_t shut_rx, u8_t shut_tx) |
mbed_official | 0:51ac1d130fd4 | 665 | { |
mbed_official | 0:51ac1d130fd4 | 666 | return netconn_close_shutdown(conn, (shut_rx ? NETCONN_SHUT_RD : 0) | (shut_tx ? NETCONN_SHUT_WR : 0)); |
mbed_official | 0:51ac1d130fd4 | 667 | } |
mbed_official | 0:51ac1d130fd4 | 668 | |
mbed_official | 0:51ac1d130fd4 | 669 | #if LWIP_IGMP |
mbed_official | 0:51ac1d130fd4 | 670 | /** |
mbed_official | 0:51ac1d130fd4 | 671 | * Join multicast groups for UDP netconns. |
mbed_official | 0:51ac1d130fd4 | 672 | * |
mbed_official | 0:51ac1d130fd4 | 673 | * @param conn the UDP netconn for which to change multicast addresses |
mbed_official | 0:51ac1d130fd4 | 674 | * @param multiaddr IP address of the multicast group to join or leave |
mbed_official | 0:51ac1d130fd4 | 675 | * @param netif_addr the IP address of the network interface on which to send |
mbed_official | 0:51ac1d130fd4 | 676 | * the igmp message |
mbed_official | 0:51ac1d130fd4 | 677 | * @param join_or_leave flag whether to send a join- or leave-message |
mbed_official | 0:51ac1d130fd4 | 678 | * @return ERR_OK if the action was taken, any err_t on error |
mbed_official | 0:51ac1d130fd4 | 679 | */ |
mbed_official | 0:51ac1d130fd4 | 680 | err_t |
mbed_official | 0:51ac1d130fd4 | 681 | netconn_join_leave_group(struct netconn *conn, |
mbed_official | 0:51ac1d130fd4 | 682 | ip_addr_t *multiaddr, |
mbed_official | 0:51ac1d130fd4 | 683 | ip_addr_t *netif_addr, |
mbed_official | 0:51ac1d130fd4 | 684 | enum netconn_igmp join_or_leave) |
mbed_official | 0:51ac1d130fd4 | 685 | { |
mbed_official | 0:51ac1d130fd4 | 686 | struct api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 687 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 688 | |
mbed_official | 0:51ac1d130fd4 | 689 | LWIP_ERROR("netconn_join_leave_group: invalid conn", (conn != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 690 | |
mbed_official | 0:51ac1d130fd4 | 691 | msg.function = do_join_leave_group; |
mbed_official | 0:51ac1d130fd4 | 692 | msg.msg.conn = conn; |
mbed_official | 0:51ac1d130fd4 | 693 | msg.msg.msg.jl.multiaddr = multiaddr; |
mbed_official | 0:51ac1d130fd4 | 694 | msg.msg.msg.jl.netif_addr = netif_addr; |
mbed_official | 0:51ac1d130fd4 | 695 | msg.msg.msg.jl.join_or_leave = join_or_leave; |
mbed_official | 0:51ac1d130fd4 | 696 | err = TCPIP_APIMSG(&msg); |
mbed_official | 0:51ac1d130fd4 | 697 | |
mbed_official | 0:51ac1d130fd4 | 698 | NETCONN_SET_SAFE_ERR(conn, err); |
mbed_official | 0:51ac1d130fd4 | 699 | return err; |
mbed_official | 0:51ac1d130fd4 | 700 | } |
mbed_official | 0:51ac1d130fd4 | 701 | #endif /* LWIP_IGMP */ |
mbed_official | 0:51ac1d130fd4 | 702 | |
mbed_official | 0:51ac1d130fd4 | 703 | #if LWIP_DNS |
mbed_official | 0:51ac1d130fd4 | 704 | /** |
mbed_official | 0:51ac1d130fd4 | 705 | * Execute a DNS query, only one IP address is returned |
mbed_official | 0:51ac1d130fd4 | 706 | * |
mbed_official | 0:51ac1d130fd4 | 707 | * @param name a string representation of the DNS host name to query |
mbed_official | 0:51ac1d130fd4 | 708 | * @param addr a preallocated ip_addr_t where to store the resolved IP address |
mbed_official | 0:51ac1d130fd4 | 709 | * @return ERR_OK: resolving succeeded |
mbed_official | 0:51ac1d130fd4 | 710 | * ERR_MEM: memory error, try again later |
mbed_official | 0:51ac1d130fd4 | 711 | * ERR_ARG: dns client not initialized or invalid hostname |
mbed_official | 0:51ac1d130fd4 | 712 | * ERR_VAL: dns server response was invalid |
mbed_official | 0:51ac1d130fd4 | 713 | */ |
mbed_official | 0:51ac1d130fd4 | 714 | err_t |
mbed_official | 0:51ac1d130fd4 | 715 | netconn_gethostbyname(const char *name, ip_addr_t *addr) |
mbed_official | 0:51ac1d130fd4 | 716 | { |
mbed_official | 0:51ac1d130fd4 | 717 | struct dns_api_msg msg; |
mbed_official | 0:51ac1d130fd4 | 718 | err_t err; |
mbed_official | 0:51ac1d130fd4 | 719 | sys_sem_t sem; |
mbed_official | 0:51ac1d130fd4 | 720 | |
mbed_official | 0:51ac1d130fd4 | 721 | LWIP_ERROR("netconn_gethostbyname: invalid name", (name != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 722 | LWIP_ERROR("netconn_gethostbyname: invalid addr", (addr != NULL), return ERR_ARG;); |
mbed_official | 0:51ac1d130fd4 | 723 | |
mbed_official | 0:51ac1d130fd4 | 724 | err = sys_sem_new(&sem, 0); |
mbed_official | 0:51ac1d130fd4 | 725 | if (err != ERR_OK) { |
mbed_official | 0:51ac1d130fd4 | 726 | return err; |
mbed_official | 0:51ac1d130fd4 | 727 | } |
mbed_official | 0:51ac1d130fd4 | 728 | |
mbed_official | 0:51ac1d130fd4 | 729 | msg.name = name; |
mbed_official | 0:51ac1d130fd4 | 730 | msg.addr = addr; |
mbed_official | 0:51ac1d130fd4 | 731 | msg.err = &err; |
mbed_official | 0:51ac1d130fd4 | 732 | msg.sem = &sem; |
mbed_official | 0:51ac1d130fd4 | 733 | |
mbed_official | 0:51ac1d130fd4 | 734 | tcpip_callback(do_gethostbyname, &msg); |
mbed_official | 0:51ac1d130fd4 | 735 | sys_sem_wait(&sem); |
mbed_official | 0:51ac1d130fd4 | 736 | sys_sem_free(&sem); |
mbed_official | 0:51ac1d130fd4 | 737 | |
mbed_official | 0:51ac1d130fd4 | 738 | return err; |
mbed_official | 0:51ac1d130fd4 | 739 | } |
mbed_official | 0:51ac1d130fd4 | 740 | #endif /* LWIP_DNS*/ |
mbed_official | 0:51ac1d130fd4 | 741 | |
mbed_official | 0:51ac1d130fd4 | 742 | #endif /* LWIP_NETCONN */ |