void ccnl_interface_enqueue(void (tx_done)(void*, int, int), struct ccnl_face_s *f, struct ccnl_relay_s *ccnl, struct ccnl_if_s *ifc, struct ccnl_buf_s *buf, sockunion *dest) { struct ccnl_txrequest_s *r; DEBUGMSG_CORE(TRACE, "enqueue interface=%p buf=%p len=%d (qlen=%d)\n", (void*)ifc, (void*)buf, buf ? buf->datalen : -1, ifc ? ifc->qlen : -1); if (ifc->qlen >= CCNL_MAX_IF_QLEN) { DEBUGMSG_CORE(WARNING, " DROPPING buf=%p\n", (void*)buf); ccnl_free(buf); return; } r = ifc->queue + ((ifc->qfront + ifc->qlen) % CCNL_MAX_IF_QLEN); r->buf = buf; memcpy(&r->dst, dest, sizeof(sockunion)); r->txdone = tx_done; r->txdone_face = f; ifc->qlen++; #ifdef USE_SCHEDULER ccnl_sched_RTS(ifc->sched, 1, buf->datalen, ccnl, ifc); #else ccnl_interface_CTS(ccnl, ifc); #endif }
void ccnl_io_loop(struct ccnl_relay_s *ccnl) { int i, maxfd = -1, rc; fd_set readfs, writefs; if (ccnl->ifcount == 0) { fprintf(stderr, "no socket to work with, not good, quitting\n"); exit(EXIT_FAILURE); } for (i = 0; i < ccnl->ifcount; i++) if (ccnl->ifs[i].sock > maxfd) maxfd = ccnl->ifs[i].sock; maxfd++; FD_ZERO(&readfs); FD_ZERO(&writefs); while(!ccnl->halt_flag) { struct timeval *timeout; for (i = 0; i < ccnl->ifcount; i++) { FD_SET(ccnl->ifs[i].sock, &readfs); if (ccnl->ifs[i].qlen > 0) FD_SET(ccnl->ifs[i].sock, &writefs); else FD_CLR(ccnl->ifs[i].sock, &writefs); } timeout = ccnl_run_events(); rc = select(maxfd, &readfs, &writefs, NULL, timeout); if (rc < 0) { perror("select(): "); exit(EXIT_FAILURE); } for (i = 0; i < ccnl->ifcount; i++) { if (FD_ISSET(ccnl->ifs[i].sock, &readfs)) { sockunion src_addr; socklen_t addrlen = sizeof(sockunion); unsigned char buf[CCNL_MAX_PACKET_SIZE]; int len; if ((len = recvfrom(ccnl->ifs[i].sock, buf, sizeof(buf), 0, (struct sockaddr*) &src_addr, &addrlen)) > 0) ccnl_core_RX(ccnl, i, buf, len, &src_addr.sa, sizeof(src_addr.ip4)); } if (FD_ISSET(ccnl->ifs[i].sock, &writefs)) ccnl_interface_CTS(&theRelay, &theRelay.ifs[0]); } } }
void ccnl_interface_enqueue(void (tx_done)(void *, int, int), struct ccnl_face_s *f, struct ccnl_relay_s *ccnl, struct ccnl_if_s *ifc, struct ccnl_buf_s *buf, sockunion *dest) { struct ccnl_txrequest_s *r; DEBUGMSG(25, "ccnl_interface_enqueue interface=%p buf=%p (qlen=%d)\n", (void *) ifc, (void *) buf, ifc->qlen); if (ifc->qlen >= CCNL_MAX_IF_QLEN) { DEBUGMSG(2, " DROPPING buf=%p\n", (void *) buf); ccnl_free(buf); return; } r = ifc->queue + ((ifc->qfront + ifc->qlen) % CCNL_MAX_IF_QLEN); r->buf = buf; memcpy(&r->dst, dest, sizeof(sockunion)); r->txdone = tx_done; r->txdone_face = f; ifc->qlen++; ccnl_interface_CTS(ccnl, ifc); }
int ccnl_io_loop(struct ccnl_relay_s *ccnl) { int i, maxfd = -1, rc; fd_set readfs, writefs; unsigned char buf[CCNL_MAX_PACKET_SIZE]; int len; if (ccnl->ifcount == 0) { fprintf(stderr, "no socket to work with, not good, quitting\n"); exit(EXIT_FAILURE); } for (i = 0; i < ccnl->ifcount; i++) if (ccnl->ifs[i].sock > maxfd) maxfd = ccnl->ifs[i].sock; maxfd++; DEBUGMSG(1, "starting main event and IO loop\n"); while(!ccnl->halt_flag) { struct timeval *timeout; FD_ZERO(&readfs); FD_ZERO(&writefs); #ifdef USE_HTTP_STATUS ccnl_http_anteselect(ccnl, ccnl->http, &readfs, &writefs, &maxfd); #endif for (i = 0; i < ccnl->ifcount; i++) { FD_SET(ccnl->ifs[i].sock, &readfs); if (ccnl->ifs[i].qlen > 0) FD_SET(ccnl->ifs[i].sock, &writefs); } timeout = ccnl_run_events(); rc = select(maxfd, &readfs, &writefs, NULL, timeout); if (rc < 0) { perror("select(): "); exit(EXIT_FAILURE); } #ifdef USE_HTTP_STATUS ccnl_http_postselect(ccnl, ccnl->http, &readfs, &writefs); #endif for (i = 0; i < ccnl->ifcount; i++) { if (FD_ISSET(ccnl->ifs[i].sock, &readfs)) { sockunion src_addr; socklen_t addrlen = sizeof(sockunion); if ((len = recvfrom(ccnl->ifs[i].sock, buf, sizeof(buf), 0, (struct sockaddr*) &src_addr, &addrlen)) > 0) { if (src_addr.sa.sa_family == AF_INET) { ccnl_core_RX(ccnl, i, buf, len, &src_addr.sa, sizeof(src_addr.ip4)); } #ifdef USE_ETHERNET else if (src_addr.sa.sa_family == AF_PACKET) { if (len > 14) ccnl_core_RX(ccnl, i, buf+14, len-14, &src_addr.sa, sizeof(src_addr.eth)); } #endif #ifdef USE_UNIXSOCKET else if (src_addr.sa.sa_family == AF_UNIX) { ccnl_core_RX(ccnl, i, buf, len, &src_addr.sa, sizeof(src_addr.ux)); } #endif } } if (FD_ISSET(ccnl->ifs[i].sock, &writefs)) { ccnl_interface_CTS(ccnl, ccnl->ifs + i); } } } return 0; }