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 #include <ubixos/types.h>
00037
00038 #include "net/debug.h"
00039 #include "net/arch.h"
00040 #include "net/api_msg.h"
00041 #include "net/memp.h"
00042 #include "net/sys.h"
00043 #include "net/tcpip.h"
00044
00045
00046 static err_t
00047 recv_tcp(void *arg, struct tcp_pcb *pcb, struct pbuf *p, err_t err)
00048 {
00049 struct netconn *conn;
00050
00051 conn = arg;
00052
00053 if(conn == NULL) {
00054 pbuf_free(p);
00055 return ERR_VAL;
00056 }
00057
00058 if(conn->recvmbox != SYS_MBOX_NULL) {
00059 conn->err = err;
00060 sys_mbox_post(conn->recvmbox, p);
00061 }
00062 return ERR_OK;
00063 }
00064
00065 static void
00066 recv_udp(void *arg, struct udp_pcb *pcb, struct pbuf *p,
00067 struct ip_addr *addr, uInt16 port)
00068 {
00069 struct netbuf *buf;
00070 struct netconn *conn;
00071
00072 conn = arg;
00073
00074 if(conn == NULL) {
00075 pbuf_free(p);
00076 return;
00077 }
00078
00079 if(conn->recvmbox != SYS_MBOX_NULL) {
00080 buf = memp_mallocp(MEMP_NETBUF);
00081 if(buf == NULL) {
00082 pbuf_free(p);
00083 return;
00084 } else {
00085 buf->p = p;
00086 buf->ptr = p;
00087 buf->fromaddr = addr;
00088 buf->fromport = port;
00089 }
00090
00091 sys_mbox_post(conn->recvmbox, buf);
00092 }
00093 }
00094
00095 static err_t
00096 poll_tcp(void *arg, struct tcp_pcb *pcb)
00097 {
00098 struct netconn *conn;
00099
00100 conn = arg;
00101 if(conn != NULL &&
00102 (conn->state == NETCONN_WRITE || conn->state == NETCONN_CLOSE) &&
00103 conn->sem != SYS_SEM_NULL) {
00104 sys_sem_signal(conn->sem);
00105 }
00106 return ERR_OK;
00107 }
00108
00109 static err_t
00110 sent_tcp(void *arg, struct tcp_pcb *pcb, uInt16 len)
00111 {
00112 struct netconn *conn;
00113
00114 conn = arg;
00115 if(conn != NULL && conn->sem != SYS_SEM_NULL) {
00116 sys_sem_signal(conn->sem);
00117 }
00118 return ERR_OK;
00119 }
00120
00121 static void
00122 err_tcp(void *arg, err_t err)
00123 {
00124 struct netconn *conn;
00125
00126 conn = arg;
00127
00128 conn->pcb.tcp = NULL;
00129
00130
00131 conn->err = err;
00132 if(conn->recvmbox != SYS_MBOX_NULL) {
00133 sys_mbox_post(conn->recvmbox, NULL);
00134 }
00135 if(conn->mbox != SYS_MBOX_NULL) {
00136 sys_mbox_post(conn->mbox, NULL);
00137 }
00138 if(conn->acceptmbox != SYS_MBOX_NULL) {
00139 sys_mbox_post(conn->acceptmbox, NULL);
00140 }
00141 if(conn->sem != SYS_SEM_NULL) {
00142 sys_sem_signal(conn->sem);
00143 }
00144 }
00145
00146 static void
00147 setup_tcp(struct netconn *conn)
00148 {
00149 struct tcp_pcb *pcb;
00150
00151 pcb = conn->pcb.tcp;
00152 tcp_arg(pcb, conn);
00153 tcp_recv(pcb, recv_tcp);
00154 tcp_sent(pcb, sent_tcp);
00155 tcp_poll(pcb, poll_tcp, 4);
00156 tcp_err(pcb, err_tcp);
00157 }
00158
00159 static err_t
00160 accept_function(void *arg, struct tcp_pcb *newpcb, err_t err)
00161 {
00162 sys_mbox_t *mbox;
00163 struct netconn *newconn;
00164
00165 #if API_MSG_DEBUG
00166 #if TCP_DEBUG
00167 tcp_debug_print_state(newpcb->state);
00168 #endif
00169 #endif
00170 mbox = (sys_mbox_t *)arg;
00171 newconn = memp_mallocp(MEMP_NETCONN);
00172 if(newconn == NULL) {
00173 return ERR_MEM;
00174 }
00175 newconn->type = NETCONN_TCP;
00176 newconn->pcb.tcp = newpcb;
00177 setup_tcp(newconn);
00178 newconn->recvmbox = sys_mbox_new();
00179 if(newconn->recvmbox == SYS_MBOX_NULL) {
00180 memp_free(MEMP_NETCONN, newconn);
00181 return ERR_MEM;
00182 }
00183 newconn->mbox = sys_mbox_new();
00184 if(newconn->mbox == SYS_MBOX_NULL) {
00185 sys_mbox_free(newconn->recvmbox);
00186 memp_free(MEMP_NETCONN, newconn);
00187 return ERR_MEM;
00188 }
00189 newconn->sem = sys_sem_new(0);
00190 if(newconn->sem == SYS_SEM_NULL) {
00191 sys_mbox_free(newconn->recvmbox);
00192 sys_mbox_free(newconn->mbox);
00193 memp_free(MEMP_NETCONN, newconn);
00194 return ERR_MEM;
00195 }
00196 newconn->acceptmbox = SYS_MBOX_NULL;
00197 newconn->err = err;
00198 sys_mbox_post(*mbox, newconn);
00199 return ERR_OK;
00200 }
00201
00202 static void
00203 do_newconn(struct api_msg_msg *msg)
00204 {
00205 }
00206
00207 static void
00208 do_delconn(struct api_msg_msg *msg)
00209 {
00210 if(msg->conn->pcb.tcp != NULL) {
00211 switch(msg->conn->type) {
00212 case NETCONN_UDPLITE:
00213
00214 case NETCONN_UDPNOCHKSUM:
00215
00216 case NETCONN_UDP:
00217 msg->conn->pcb.udp->recv_arg = NULL;
00218 udp_remove(msg->conn->pcb.udp);
00219 break;
00220 case NETCONN_TCP:
00221 tcp_arg(msg->conn->pcb.tcp, NULL);
00222 tcp_sent(msg->conn->pcb.tcp, NULL);
00223 tcp_recv(msg->conn->pcb.tcp, NULL);
00224 tcp_accept(msg->conn->pcb.tcp, NULL);
00225 tcp_poll(msg->conn->pcb.tcp, NULL, 0);
00226 tcp_err(msg->conn->pcb.tcp, NULL);
00227 if(msg->conn->pcb.tcp->state == LISTEN) {
00228 tcp_close(msg->conn->pcb.tcp);
00229 } else {
00230 if(tcp_close(msg->conn->pcb.tcp) != ERR_OK) {
00231 tcp_abort(msg->conn->pcb.tcp);
00232 }
00233 }
00234 break;
00235 }
00236 }
00237 if(msg->conn->mbox != SYS_MBOX_NULL) {
00238 sys_mbox_post(msg->conn->mbox, NULL);
00239 }
00240 }
00241
00242 static void
00243 do_bind(struct api_msg_msg *msg)
00244 {
00245 if(msg->conn->pcb.tcp == NULL) {
00246 switch(msg->conn->type) {
00247 case NETCONN_UDPLITE:
00248 msg->conn->pcb.udp = udp_new();
00249 udp_setflags(msg->conn->pcb.udp, UDP_FLAGS_UDPLITE);
00250 udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);
00251 break;
00252 case NETCONN_UDPNOCHKSUM:
00253 msg->conn->pcb.udp = udp_new();
00254 udp_setflags(msg->conn->pcb.udp, UDP_FLAGS_NOCHKSUM);
00255 udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);
00256 break;
00257 case NETCONN_UDP:
00258 msg->conn->pcb.udp = udp_new();
00259 udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);
00260 break;
00261 case NETCONN_TCP:
00262 msg->conn->pcb.tcp = tcp_new();
00263 setup_tcp(msg->conn);
00264 break;
00265 }
00266 }
00267 switch(msg->conn->type) {
00268 case NETCONN_UDPLITE:
00269
00270 case NETCONN_UDPNOCHKSUM:
00271
00272 case NETCONN_UDP:
00273 udp_bind(msg->conn->pcb.udp, msg->msg.bc.ipaddr, msg->msg.bc.port);
00274 break;
00275 case NETCONN_TCP:
00276 msg->conn->err = tcp_bind(msg->conn->pcb.tcp,
00277 msg->msg.bc.ipaddr, msg->msg.bc.port);
00278 break;
00279 }
00280 sys_mbox_post(msg->conn->mbox, NULL);
00281 }
00282
00283 static err_t
00284 do_connected(void *arg, struct tcp_pcb *pcb, err_t err)
00285 {
00286 struct netconn *conn;
00287
00288 conn = arg;
00289
00290 if(conn == NULL) {
00291 return ERR_VAL;
00292 }
00293
00294 conn->err = err;
00295
00296 if(conn->type == NETCONN_TCP && err == ERR_OK) {
00297 setup_tcp(conn);
00298 }
00299
00300 sys_mbox_post(conn->mbox, NULL);
00301 return ERR_OK;
00302 }
00303
00304 static void
00305 do_connect(struct api_msg_msg *msg)
00306 {
00307 if(msg->conn->pcb.tcp == NULL) {
00308 switch(msg->conn->type) {
00309 case NETCONN_UDPLITE:
00310 msg->conn->pcb.udp = udp_new();
00311 if(msg->conn->pcb.udp == NULL) {
00312 msg->conn->err = ERR_MEM;
00313 sys_mbox_post(msg->conn->mbox, NULL);
00314 return;
00315 }
00316 udp_setflags(msg->conn->pcb.udp, UDP_FLAGS_UDPLITE);
00317 udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);
00318 break;
00319 case NETCONN_UDPNOCHKSUM:
00320 msg->conn->pcb.udp = udp_new();
00321 if(msg->conn->pcb.udp == NULL) {
00322 msg->conn->err = ERR_MEM;
00323 sys_mbox_post(msg->conn->mbox, NULL);
00324 return;
00325 }
00326 udp_setflags(msg->conn->pcb.udp, UDP_FLAGS_NOCHKSUM);
00327 udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);
00328 break;
00329 case NETCONN_UDP:
00330 msg->conn->pcb.udp = udp_new();
00331 if(msg->conn->pcb.udp == NULL) {
00332 msg->conn->err = ERR_MEM;
00333 sys_mbox_post(msg->conn->mbox, NULL);
00334 return;
00335 }
00336 udp_recv(msg->conn->pcb.udp, recv_udp, msg->conn);
00337 break;
00338 case NETCONN_TCP:
00339 msg->conn->pcb.tcp = tcp_new();
00340 if(msg->conn->pcb.tcp == NULL) {
00341 msg->conn->err = ERR_MEM;
00342 sys_mbox_post(msg->conn->mbox, NULL);
00343 return;
00344 }
00345 break;
00346 }
00347 }
00348 switch(msg->conn->type) {
00349 case NETCONN_UDPLITE:
00350
00351 case NETCONN_UDPNOCHKSUM:
00352
00353 case NETCONN_UDP:
00354 udp_connect(msg->conn->pcb.udp, msg->msg.bc.ipaddr, msg->msg.bc.port);
00355 sys_mbox_post(msg->conn->mbox, NULL);
00356 break;
00357 case NETCONN_TCP:
00358
00359 setup_tcp(msg->conn);
00360 tcp_connect(msg->conn->pcb.tcp, msg->msg.bc.ipaddr, msg->msg.bc.port,
00361 do_connected);
00362
00363 break;
00364 }
00365 }
00366
00367 static void
00368 do_listen(struct api_msg_msg *msg)
00369 {
00370 if(msg->conn->pcb.tcp != NULL) {
00371 switch(msg->conn->type) {
00372 case NETCONN_UDPLITE:
00373
00374 case NETCONN_UDPNOCHKSUM:
00375
00376 case NETCONN_UDP:
00377 DEBUGF(API_MSG_DEBUG, ("api_msg: listen UDP: cannot listen for UDP.\n"));
00378 break;
00379 case NETCONN_TCP:
00380 msg->conn->pcb.tcp = tcp_listen(msg->conn->pcb.tcp);
00381 if(msg->conn->pcb.tcp == NULL) {
00382 msg->conn->err = ERR_MEM;
00383 } else {
00384 if(msg->conn->acceptmbox == SYS_MBOX_NULL) {
00385 msg->conn->acceptmbox = sys_mbox_new();
00386 if(msg->conn->acceptmbox == SYS_MBOX_NULL) {
00387 msg->conn->err = ERR_MEM;
00388 break;
00389 }
00390 }
00391 tcp_arg(msg->conn->pcb.tcp, (void *)&(msg->conn->acceptmbox));
00392 tcp_accept(msg->conn->pcb.tcp, accept_function);
00393 }
00394 break;
00395 }
00396 }
00397 sys_mbox_post(msg->conn->mbox, NULL);
00398 }
00399
00400 static void
00401 do_accept(struct api_msg_msg *msg)
00402 {
00403 if(msg->conn->pcb.tcp != NULL) {
00404 switch(msg->conn->type) {
00405 case NETCONN_UDPLITE:
00406
00407 case NETCONN_UDPNOCHKSUM:
00408
00409 case NETCONN_UDP:
00410 DEBUGF(API_MSG_DEBUG, ("api_msg: accept UDP: cannot accept for UDP.\n"));
00411 break;
00412 case NETCONN_TCP:
00413 break;
00414 }
00415 }
00416 }
00417
00418 static void
00419 do_send(struct api_msg_msg *msg)
00420 {
00421 if(msg->conn->pcb.tcp != NULL) {
00422 switch(msg->conn->type) {
00423 case NETCONN_UDPLITE:
00424
00425 case NETCONN_UDPNOCHKSUM:
00426
00427 case NETCONN_UDP:
00428 udp_send(msg->conn->pcb.udp, msg->msg.p);
00429 break;
00430 case NETCONN_TCP:
00431 break;
00432 }
00433 }
00434 sys_mbox_post(msg->conn->mbox, NULL);
00435 }
00436
00437 static void
00438 do_recv(struct api_msg_msg *msg)
00439 {
00440 if(msg->conn->pcb.tcp != NULL) {
00441 if(msg->conn->type == NETCONN_TCP) {
00442 tcp_recved(msg->conn->pcb.tcp, msg->msg.len);
00443 }
00444 }
00445 sys_mbox_post(msg->conn->mbox, NULL);
00446 }
00447
00448 static void
00449 do_write(struct api_msg_msg *msg)
00450 {
00451 err_t err;
00452 if(msg->conn->pcb.tcp != NULL) {
00453 switch(msg->conn->type) {
00454 case NETCONN_UDPLITE:
00455
00456 case NETCONN_UDPNOCHKSUM:
00457
00458 case NETCONN_UDP:
00459 msg->conn->err = ERR_VAL;
00460 break;
00461 case NETCONN_TCP:
00462 err = tcp_write(msg->conn->pcb.tcp, msg->msg.w.dataptr,
00463 msg->msg.w.len, msg->msg.w.copy);
00464
00465
00466
00467
00468 if(err == ERR_OK && msg->conn->pcb.tcp->unacked == NULL) {
00469 tcp_output(msg->conn->pcb.tcp);
00470 }
00471 msg->conn->err = err;
00472 break;
00473 }
00474 }
00475 sys_mbox_post(msg->conn->mbox, NULL);
00476 }
00477
00478 static void
00479 do_close(struct api_msg_msg *msg)
00480 {
00481 err_t err;
00482 if(msg->conn->pcb.tcp != NULL) {
00483 switch(msg->conn->type) {
00484 case NETCONN_UDPLITE:
00485
00486 case NETCONN_UDPNOCHKSUM:
00487
00488 case NETCONN_UDP:
00489 break;
00490 case NETCONN_TCP:
00491 if(msg->conn->pcb.tcp->state == LISTEN) {
00492 err = tcp_close(msg->conn->pcb.tcp);
00493 } else {
00494 err = tcp_close(msg->conn->pcb.tcp);
00495 }
00496 msg->conn->err = err;
00497 break;
00498 }
00499 }
00500 sys_mbox_post(msg->conn->mbox, NULL);
00501 }
00502
00503 typedef void (* api_msg_decode)(struct api_msg_msg *msg);
00504 static api_msg_decode decode[API_MSG_MAX] = {
00505 do_newconn,
00506 do_delconn,
00507 do_bind,
00508 do_connect,
00509 do_listen,
00510 do_accept,
00511 do_send,
00512 do_recv,
00513 do_write,
00514 do_close
00515 };
00516 void
00517 api_msg_input(struct api_msg *msg)
00518 {
00519 decode[msg->type](&(msg->msg));
00520 }
00521
00522 void
00523 api_msg_post(struct api_msg *msg)
00524 {
00525 tcpip_apimsg(msg);
00526 }
00527
00528
00529