00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042 #include "lwip/opt.h"
00043
00044 #if LWIP_NETCONN
00045
00046 #include "lwip/api.h"
00047 #include "lwip/tcpip.h"
00048 #include "lwip/memp.h"
00049
00050 #include "lwip/ip.h"
00051 #include "lwip/raw.h"
00052 #include "lwip/udp.h"
00053 #include "lwip/tcp.h"
00054
00055 #include <string.h>
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067 struct netconn*
00068 netconn_new_with_proto_and_callback(enum netconn_type t, u8_t proto, netconn_callback callback)
00069 {
00070 struct netconn *conn;
00071 struct api_msg msg;
00072
00073 conn = netconn_alloc(t, callback);
00074 if (conn != NULL ) {
00075 msg.function = do_newconn;
00076 msg.msg.msg.n.proto = proto;
00077 msg.msg.conn = conn;
00078 TCPIP_APIMSG(&msg);
00079
00080 if (conn->err != ERR_OK) {
00081 LWIP_ASSERT("freeing conn without freeing pcb", conn->pcb.tcp == NULL);
00082 LWIP_ASSERT("conn has no op_completed", conn->op_completed != SYS_SEM_NULL);
00083 LWIP_ASSERT("conn has no recvmbox", conn->recvmbox != SYS_MBOX_NULL);
00084 LWIP_ASSERT("conn->acceptmbox shouldn't exist", conn->acceptmbox == SYS_MBOX_NULL);
00085 sys_sem_free(conn->op_completed);
00086 sys_mbox_free(conn->recvmbox);
00087 memp_free(MEMP_NETCONN, conn);
00088 return NULL;
00089 }
00090 }
00091 return conn;
00092 }
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102 err_t
00103 netconn_delete(struct netconn *conn)
00104 {
00105 struct api_msg msg;
00106
00107
00108 if (conn == NULL) {
00109 return ERR_OK;
00110 }
00111
00112 msg.function = do_delconn;
00113 msg.msg.conn = conn;
00114 tcpip_apimsg(&msg);
00115
00116 conn->pcb.tcp = NULL;
00117 netconn_free(conn);
00118
00119 return ERR_OK;
00120 }
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133 err_t
00134 netconn_getaddr(struct netconn *conn, struct ip_addr *addr, u16_t *port, u8_t local)
00135 {
00136 struct api_msg msg;
00137
00138 LWIP_ERROR("netconn_getaddr: invalid conn", (conn != NULL), return ERR_ARG;);
00139 LWIP_ERROR("netconn_getaddr: invalid addr", (addr != NULL), return ERR_ARG;);
00140 LWIP_ERROR("netconn_getaddr: invalid port", (port != NULL), return ERR_ARG;);
00141
00142 msg.function = do_getaddr;
00143 msg.msg.conn = conn;
00144 msg.msg.msg.ad.ipaddr = addr;
00145 msg.msg.msg.ad.port = port;
00146 msg.msg.msg.ad.local = local;
00147 TCPIP_APIMSG(&msg);
00148
00149 return conn->err;
00150 }
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162 err_t
00163 netconn_bind(struct netconn *conn, struct ip_addr *addr, u16_t port)
00164 {
00165 struct api_msg msg;
00166
00167 LWIP_ERROR("netconn_bind: invalid conn", (conn != NULL), return ERR_ARG;);
00168
00169 msg.function = do_bind;
00170 msg.msg.conn = conn;
00171 msg.msg.msg.bc.ipaddr = addr;
00172 msg.msg.msg.bc.port = port;
00173 TCPIP_APIMSG(&msg);
00174 return conn->err;
00175 }
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185 err_t
00186 netconn_connect(struct netconn *conn, struct ip_addr *addr, u16_t port)
00187 {
00188 struct api_msg msg;
00189
00190 LWIP_ERROR("netconn_connect: invalid conn", (conn != NULL), return ERR_ARG;);
00191
00192 msg.function = do_connect;
00193 msg.msg.conn = conn;
00194 msg.msg.msg.bc.ipaddr = addr;
00195 msg.msg.msg.bc.port = port;
00196
00197 tcpip_apimsg(&msg);
00198 return conn->err;
00199 }
00200
00201
00202
00203
00204
00205
00206
00207 err_t
00208 netconn_disconnect(struct netconn *conn)
00209 {
00210 struct api_msg msg;
00211
00212 LWIP_ERROR("netconn_disconnect: invalid conn", (conn != NULL), return ERR_ARG;);
00213
00214 msg.function = do_disconnect;
00215 msg.msg.conn = conn;
00216 TCPIP_APIMSG(&msg);
00217 return conn->err;
00218 }
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228 err_t
00229 netconn_listen_with_backlog(struct netconn *conn, u8_t backlog)
00230 {
00231 struct api_msg msg;
00232
00233
00234 LWIP_UNUSED_ARG(backlog);
00235
00236 LWIP_ERROR("netconn_listen: invalid conn", (conn != NULL), return ERR_ARG;);
00237
00238 msg.function = do_listen;
00239 msg.msg.conn = conn;
00240 #if TCP_LISTEN_BACKLOG
00241 msg.msg.msg.lb.backlog = backlog;
00242 #endif
00243 TCPIP_APIMSG(&msg);
00244 return conn->err;
00245 }
00246
00247
00248
00249
00250
00251
00252
00253 struct netconn *
00254 netconn_accept(struct netconn *conn)
00255 {
00256 struct netconn *newconn;
00257
00258 LWIP_ERROR("netconn_accept: invalid conn", (conn != NULL), return NULL;);
00259 LWIP_ERROR("netconn_accept: invalid acceptmbox", (conn->acceptmbox != SYS_MBOX_NULL), return NULL;);
00260
00261 #if LWIP_SO_RCVTIMEO
00262 if (sys_arch_mbox_fetch(conn->acceptmbox, (void *)&newconn, conn->recv_timeout) == SYS_ARCH_TIMEOUT) {
00263 newconn = NULL;
00264 } else
00265 #else
00266 sys_arch_mbox_fetch(conn->acceptmbox, (void *)&newconn, 0);
00267 #endif
00268 {
00269
00270 API_EVENT(conn, NETCONN_EVT_RCVMINUS, 0);
00271
00272 #if TCP_LISTEN_BACKLOG
00273 if (newconn != NULL) {
00274
00275 struct api_msg msg;
00276 msg.function = do_recv;
00277 msg.msg.conn = conn;
00278 TCPIP_APIMSG(&msg);
00279 }
00280 #endif
00281 }
00282
00283 return newconn;
00284 }
00285
00286
00287
00288
00289
00290
00291
00292 struct netbuf *
00293 netconn_recv(struct netconn *conn)
00294 {
00295 struct api_msg msg;
00296 struct netbuf *buf = NULL;
00297 struct pbuf *p;
00298 u16_t len;
00299
00300 LWIP_ERROR("netconn_recv: invalid conn", (conn != NULL), return NULL;);
00301
00302 if (conn->recvmbox == SYS_MBOX_NULL) {
00303
00304
00305 conn->err = ERR_CONN;
00306 return NULL;
00307 }
00308
00309 if (ERR_IS_FATAL(conn->err)) {
00310 return NULL;
00311 }
00312
00313 if (conn->type == NETCONN_TCP) {
00314 #if LWIP_TCP
00315 if (conn->state == NETCONN_LISTEN) {
00316
00317 conn->err = ERR_CONN;
00318 return NULL;
00319 }
00320
00321 buf = memp_malloc(MEMP_NETBUF);
00322
00323 if (buf == NULL) {
00324 conn->err = ERR_MEM;
00325 return NULL;
00326 }
00327
00328 #if LWIP_SO_RCVTIMEO
00329 if (sys_arch_mbox_fetch(conn->recvmbox, (void *)&p, conn->recv_timeout)==SYS_ARCH_TIMEOUT) {
00330 memp_free(MEMP_NETBUF, buf);
00331 conn->err = ERR_TIMEOUT;
00332 return NULL;
00333 }
00334 #else
00335 sys_arch_mbox_fetch(conn->recvmbox, (void *)&p, 0);
00336 #endif
00337
00338 if (p != NULL) {
00339 len = p->tot_len;
00340 SYS_ARCH_DEC(conn->recv_avail, len);
00341 } else {
00342 len = 0;
00343 }
00344
00345
00346 API_EVENT(conn, NETCONN_EVT_RCVMINUS, len);
00347
00348
00349 if (p == NULL) {
00350 memp_free(MEMP_NETBUF, buf);
00351
00352 if (conn->err == ERR_OK) {
00353 conn->err = ERR_CLSD;
00354 }
00355 return NULL;
00356 }
00357
00358 buf->p = p;
00359 buf->ptr = p;
00360 buf->port = 0;
00361 buf->addr = NULL;
00362
00363
00364 msg.function = do_recv;
00365 msg.msg.conn = conn;
00366 if (buf != NULL) {
00367 msg.msg.msg.r.len = buf->p->tot_len;
00368 } else {
00369 msg.msg.msg.r.len = 1;
00370 }
00371 TCPIP_APIMSG(&msg);
00372 #endif
00373 } else {
00374 #if (LWIP_UDP || LWIP_RAW)
00375 #if LWIP_SO_RCVTIMEO
00376 if (sys_arch_mbox_fetch(conn->recvmbox, (void *)&buf, conn->recv_timeout)==SYS_ARCH_TIMEOUT) {
00377 buf = NULL;
00378 }
00379 #else
00380 sys_arch_mbox_fetch(conn->recvmbox, (void *)&buf, 0);
00381 #endif
00382 if (buf!=NULL) {
00383 SYS_ARCH_DEC(conn->recv_avail, buf->p->tot_len);
00384
00385 API_EVENT(conn, NETCONN_EVT_RCVMINUS, buf->p->tot_len);
00386 }
00387 #endif
00388 }
00389
00390 LWIP_DEBUGF(API_LIB_DEBUG, ("netconn_recv: received %p (err %d)\n", (void *)buf, conn->err));
00391
00392 return buf;
00393 }
00394
00395
00396
00397
00398
00399
00400
00401
00402
00403
00404
00405 err_t
00406 netconn_sendto(struct netconn *conn, struct netbuf *buf, struct ip_addr *addr, u16_t port)
00407 {
00408 if (buf != NULL) {
00409 buf->addr = addr;
00410 buf->port = port;
00411 return netconn_send(conn, buf);
00412 }
00413 return ERR_VAL;
00414 }
00415
00416
00417
00418
00419
00420
00421
00422
00423 err_t
00424 netconn_send(struct netconn *conn, struct netbuf *buf)
00425 {
00426 struct api_msg msg;
00427
00428 LWIP_ERROR("netconn_send: invalid conn", (conn != NULL), return ERR_ARG;);
00429
00430 LWIP_DEBUGF(API_LIB_DEBUG, ("netconn_send: sending %"U16_F" bytes\n", buf->p->tot_len));
00431 msg.function = do_send;
00432 msg.msg.conn = conn;
00433 msg.msg.msg.b = buf;
00434 TCPIP_APIMSG(&msg);
00435 return conn->err;
00436 }
00437
00438
00439
00440
00441
00442
00443
00444
00445
00446
00447
00448
00449 err_t
00450 netconn_write(struct netconn *conn, const void *dataptr, size_t size, u8_t apiflags)
00451 {
00452 struct api_msg msg;
00453
00454 LWIP_ERROR("netconn_write: invalid conn", (conn != NULL), return ERR_ARG;);
00455 LWIP_ERROR("netconn_write: invalid conn->type", (conn->type == NETCONN_TCP), return ERR_VAL;);
00456
00457 msg.function = do_write;
00458 msg.msg.conn = conn;
00459 msg.msg.msg.w.dataptr = dataptr;
00460 msg.msg.msg.w.apiflags = apiflags;
00461 msg.msg.msg.w.len = size;
00462
00463
00464
00465 TCPIP_APIMSG(&msg);
00466 return conn->err;
00467 }
00468
00469
00470
00471
00472
00473
00474
00475 err_t
00476 netconn_close(struct netconn *conn)
00477 {
00478 struct api_msg msg;
00479
00480 LWIP_ERROR("netconn_close: invalid conn", (conn != NULL), return ERR_ARG;);
00481
00482 msg.function = do_close;
00483 msg.msg.conn = conn;
00484 tcpip_apimsg(&msg);
00485 return conn->err;
00486 }
00487
00488 #if LWIP_IGMP
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499 err_t
00500 netconn_join_leave_group(struct netconn *conn,
00501 struct ip_addr *multiaddr,
00502 struct ip_addr *interface,
00503 enum netconn_igmp join_or_leave)
00504 {
00505 struct api_msg msg;
00506
00507 LWIP_ERROR("netconn_join_leave_group: invalid conn", (conn != NULL), return ERR_ARG;);
00508
00509 msg.function = do_join_leave_group;
00510 msg.msg.conn = conn;
00511 msg.msg.msg.jl.multiaddr = multiaddr;
00512 msg.msg.msg.jl.interface = interface;
00513 msg.msg.msg.jl.join_or_leave = join_or_leave;
00514 TCPIP_APIMSG(&msg);
00515 return conn->err;
00516 }
00517 #endif
00518
00519 #if LWIP_DNS
00520
00521
00522
00523
00524
00525
00526
00527
00528
00529
00530 err_t
00531 netconn_gethostbyname(const char *name, struct ip_addr *addr)
00532 {
00533 struct dns_api_msg msg;
00534 err_t err;
00535 sys_sem_t sem;
00536
00537 LWIP_ERROR("netconn_gethostbyname: invalid name", (name != NULL), return ERR_ARG;);
00538 LWIP_ERROR("netconn_gethostbyname: invalid addr", (addr != NULL), return ERR_ARG;);
00539
00540 sem = sys_sem_new(0);
00541 if (sem == SYS_SEM_NULL) {
00542 return ERR_MEM;
00543 }
00544
00545 msg.name = name;
00546 msg.addr = addr;
00547 msg.err = &err;
00548 msg.sem = sem;
00549
00550 tcpip_callback(do_gethostbyname, &msg);
00551 sys_sem_wait(sem);
00552 sys_sem_free(sem);
00553
00554 return err;
00555 }
00556 #endif
00557
00558 #endif