|
|
|
|
@ -42,352 +42,352 @@ err_t tapif_init(struct netif *netif)
|
|
|
|
|
|
|
|
|
|
err_t low_level_output(struct netif *netif, struct pbuf *p) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
struct pbuf *q; |
|
|
|
|
char buf[ZT_MAX_MTU+32]; |
|
|
|
|
char *bufptr; |
|
|
|
|
int totalLength = 0; |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
struct pbuf *q; |
|
|
|
|
char buf[ZT_MAX_MTU+32]; |
|
|
|
|
char *bufptr; |
|
|
|
|
int totalLength = 0; |
|
|
|
|
|
|
|
|
|
ZeroTier::SocketTap *tap = (ZeroTier::SocketTap*)netif->state; |
|
|
|
|
bufptr = buf; |
|
|
|
|
// Copy data from each pbuf, one at a time
|
|
|
|
|
for(q = p; q != NULL; q = q->next) { |
|
|
|
|
memcpy(bufptr, q->payload, q->len); |
|
|
|
|
bufptr += q->len; |
|
|
|
|
totalLength += q->len; |
|
|
|
|
} |
|
|
|
|
// Split ethernet header and feed into handler
|
|
|
|
|
struct eth_hdr *ethhdr; |
|
|
|
|
ethhdr = (struct eth_hdr *)buf; |
|
|
|
|
ZeroTier::SocketTap *tap = (ZeroTier::SocketTap*)netif->state; |
|
|
|
|
bufptr = buf; |
|
|
|
|
// Copy data from each pbuf, one at a time
|
|
|
|
|
for(q = p; q != NULL; q = q->next) { |
|
|
|
|
memcpy(bufptr, q->payload, q->len); |
|
|
|
|
bufptr += q->len; |
|
|
|
|
totalLength += q->len; |
|
|
|
|
} |
|
|
|
|
// Split ethernet header and feed into handler
|
|
|
|
|
struct eth_hdr *ethhdr; |
|
|
|
|
ethhdr = (struct eth_hdr *)buf; |
|
|
|
|
|
|
|
|
|
ZeroTier::MAC src_mac; |
|
|
|
|
ZeroTier::MAC dest_mac; |
|
|
|
|
src_mac.setTo(ethhdr->src.addr, 6); |
|
|
|
|
dest_mac.setTo(ethhdr->dest.addr, 6); |
|
|
|
|
ZeroTier::MAC src_mac; |
|
|
|
|
ZeroTier::MAC dest_mac; |
|
|
|
|
src_mac.setTo(ethhdr->src.addr, 6); |
|
|
|
|
dest_mac.setTo(ethhdr->dest.addr, 6); |
|
|
|
|
|
|
|
|
|
tap->_handler(tap->_arg,NULL,tap->_nwid,src_mac,dest_mac, |
|
|
|
|
ZeroTier::Utils::ntoh((uint16_t)ethhdr->type),0,buf + sizeof(struct eth_hdr),totalLength - sizeof(struct eth_hdr)); |
|
|
|
|
return ERR_OK; |
|
|
|
|
tap->_handler(tap->_arg,NULL,tap->_nwid,src_mac,dest_mac, |
|
|
|
|
ZeroTier::Utils::ntoh((uint16_t)ethhdr->type),0,buf + sizeof(struct eth_hdr),totalLength - sizeof(struct eth_hdr)); |
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
namespace ZeroTier |
|
|
|
|
{ |
|
|
|
|
void lwIP::lwip_init_interface(SocketTap *tap, const InetAddress &ip) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
Mutex::Lock _l(tap->_ips_m); |
|
|
|
|
void lwIP::lwip_init_interface(SocketTap *tap, const InetAddress &ip) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
Mutex::Lock _l(tap->_ips_m); |
|
|
|
|
|
|
|
|
|
if (std::find(tap->_ips.begin(),tap->_ips.end(),ip) == tap->_ips.end()) { |
|
|
|
|
tap->_ips.push_back(ip); |
|
|
|
|
std::sort(tap->_ips.begin(),tap->_ips.end()); |
|
|
|
|
if (std::find(tap->_ips.begin(),tap->_ips.end(),ip) == tap->_ips.end()) { |
|
|
|
|
tap->_ips.push_back(ip); |
|
|
|
|
std::sort(tap->_ips.begin(),tap->_ips.end()); |
|
|
|
|
#if defined(LIBZT_IPV4) |
|
|
|
|
if (ip.isV4()) { |
|
|
|
|
// Set IP
|
|
|
|
|
static ip_addr_t ipaddr, netmask, gw; |
|
|
|
|
IP4_ADDR(&gw,127,0,0,1); |
|
|
|
|
ipaddr.addr = *((u32_t *)ip.rawIpData()); |
|
|
|
|
netmask.addr = *((u32_t *)ip.netmask().rawIpData()); |
|
|
|
|
netif_add(&(tap->lwipdev),&ipaddr, &netmask, &gw, NULL, tapif_init, ethernet_input); |
|
|
|
|
tap->lwipdev.state = tap; |
|
|
|
|
tap->lwipdev.output = etharp_output; |
|
|
|
|
tap->_mac.copyTo(tap->lwipdev.hwaddr, 6); |
|
|
|
|
tap->lwipdev.mtu = tap->_mtu; |
|
|
|
|
tap->lwipdev.name[0] = 'l'; |
|
|
|
|
tap->lwipdev.name[1] = '4'; |
|
|
|
|
tap->lwipdev.linkoutput = low_level_output; |
|
|
|
|
tap->lwipdev.hwaddr_len = 6; |
|
|
|
|
tap->lwipdev.flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_IGMP | NETIF_FLAG_LINK_UP | NETIF_FLAG_UP; |
|
|
|
|
netif_set_default(&(tap->lwipdev)); |
|
|
|
|
netif_set_up(&(tap->lwipdev)); |
|
|
|
|
DEBUG_INFO("addr=%s, netmask=%s", ip.toString().c_str(), ip.netmask().toString().c_str()); |
|
|
|
|
} |
|
|
|
|
if (ip.isV4()) { |
|
|
|
|
// Set IP
|
|
|
|
|
static ip_addr_t ipaddr, netmask, gw; |
|
|
|
|
IP4_ADDR(&gw,127,0,0,1); |
|
|
|
|
ipaddr.addr = *((u32_t *)ip.rawIpData()); |
|
|
|
|
netmask.addr = *((u32_t *)ip.netmask().rawIpData()); |
|
|
|
|
netif_add(&(tap->lwipdev),&ipaddr, &netmask, &gw, NULL, tapif_init, ethernet_input); |
|
|
|
|
tap->lwipdev.state = tap; |
|
|
|
|
tap->lwipdev.output = etharp_output; |
|
|
|
|
tap->_mac.copyTo(tap->lwipdev.hwaddr, 6); |
|
|
|
|
tap->lwipdev.mtu = tap->_mtu; |
|
|
|
|
tap->lwipdev.name[0] = 'l'; |
|
|
|
|
tap->lwipdev.name[1] = '4'; |
|
|
|
|
tap->lwipdev.linkoutput = low_level_output; |
|
|
|
|
tap->lwipdev.hwaddr_len = 6; |
|
|
|
|
tap->lwipdev.flags = NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_IGMP | NETIF_FLAG_LINK_UP | NETIF_FLAG_UP; |
|
|
|
|
netif_set_default(&(tap->lwipdev)); |
|
|
|
|
netif_set_up(&(tap->lwipdev)); |
|
|
|
|
DEBUG_INFO("addr=%s, netmask=%s", ip.toString().c_str(), ip.netmask().toString().c_str()); |
|
|
|
|
} |
|
|
|
|
#endif |
|
|
|
|
#if defined(LIBZT_IPV6) |
|
|
|
|
if(ip.isV6()) { |
|
|
|
|
DEBUG_INFO("local_addr=%s", ip.toString().c_str()); |
|
|
|
|
static ip6_addr_t addr6; |
|
|
|
|
struct sockaddr_in6 in6; |
|
|
|
|
memcpy(in6.sin6_addr.s6_addr,ip.rawIpData(),16); |
|
|
|
|
in6_to_ip6((ip6_addr *)&addr6, &in6); |
|
|
|
|
tap->lwipdev6.mtu = tap->_mtu; |
|
|
|
|
tap->lwipdev6.name[0] = 'l'; |
|
|
|
|
tap->lwipdev6.name[1] = '6'; |
|
|
|
|
tap->lwipdev6.hwaddr_len = 6; |
|
|
|
|
tap->lwipdev6.linkoutput = low_level_output; |
|
|
|
|
tap->lwipdev6.ip6_autoconfig_enabled = 1; |
|
|
|
|
tap->_mac.copyTo(tap->lwipdev6.hwaddr, tap->lwipdev6.hwaddr_len); |
|
|
|
|
netif_create_ip6_linklocal_address(&(tap->lwipdev6), 1); |
|
|
|
|
netif_add(&(tap->lwipdev6), NULL, tapif_init, ethernet_input); |
|
|
|
|
netif_set_default(&(tap->lwipdev6)); |
|
|
|
|
netif_set_up(&(tap->lwipdev6));
|
|
|
|
|
netif_ip6_addr_set_state(&(tap->lwipdev6), 1, IP6_ADDR_TENTATIVE);
|
|
|
|
|
ip6_addr_copy(ip_2_ip6(tap->lwipdev6.ip6_addr[1]), addr6); |
|
|
|
|
tap->lwipdev6.output_ip6 = ethip6_output; |
|
|
|
|
tap->lwipdev6.state = tap; |
|
|
|
|
tap->lwipdev6.flags = NETIF_FLAG_LINK_UP | NETIF_FLAG_UP; |
|
|
|
|
DEBUG_INFO("addr=%s, netmask=%s", ip.toString().c_str(), ip.netmask().toString().c_str()); |
|
|
|
|
} |
|
|
|
|
if(ip.isV6()) { |
|
|
|
|
DEBUG_INFO("local_addr=%s", ip.toString().c_str()); |
|
|
|
|
static ip6_addr_t addr6; |
|
|
|
|
struct sockaddr_in6 in6; |
|
|
|
|
memcpy(in6.sin6_addr.s6_addr,ip.rawIpData(),16); |
|
|
|
|
in6_to_ip6((ip6_addr *)&addr6, &in6); |
|
|
|
|
tap->lwipdev6.mtu = tap->_mtu; |
|
|
|
|
tap->lwipdev6.name[0] = 'l'; |
|
|
|
|
tap->lwipdev6.name[1] = '6'; |
|
|
|
|
tap->lwipdev6.hwaddr_len = 6; |
|
|
|
|
tap->lwipdev6.linkoutput = low_level_output; |
|
|
|
|
tap->lwipdev6.ip6_autoconfig_enabled = 1; |
|
|
|
|
tap->_mac.copyTo(tap->lwipdev6.hwaddr, tap->lwipdev6.hwaddr_len); |
|
|
|
|
netif_create_ip6_linklocal_address(&(tap->lwipdev6), 1); |
|
|
|
|
netif_add(&(tap->lwipdev6), NULL, tapif_init, ethernet_input); |
|
|
|
|
netif_set_default(&(tap->lwipdev6)); |
|
|
|
|
netif_set_up(&(tap->lwipdev6));
|
|
|
|
|
netif_ip6_addr_set_state(&(tap->lwipdev6), 1, IP6_ADDR_TENTATIVE);
|
|
|
|
|
ip6_addr_copy(ip_2_ip6(tap->lwipdev6.ip6_addr[1]), addr6); |
|
|
|
|
tap->lwipdev6.output_ip6 = ethip6_output; |
|
|
|
|
tap->lwipdev6.state = tap; |
|
|
|
|
tap->lwipdev6.flags = NETIF_FLAG_LINK_UP | NETIF_FLAG_UP; |
|
|
|
|
DEBUG_INFO("addr=%s, netmask=%s", ip.toString().c_str(), ip.netmask().toString().c_str()); |
|
|
|
|
} |
|
|
|
|
#endif |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void lwIP::lwip_loop(SocketTap *tap) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
uint64_t prev_tcp_time = 0, prev_status_time = 0, prev_discovery_time = 0; |
|
|
|
|
while(tap->_run) |
|
|
|
|
{ |
|
|
|
|
uint64_t now = OSUtils::now(); |
|
|
|
|
uint64_t since_tcp = now - prev_tcp_time; |
|
|
|
|
uint64_t since_discovery = now - prev_discovery_time; |
|
|
|
|
uint64_t since_status = now - prev_status_time; |
|
|
|
|
uint64_t tcp_remaining = LWIP_TCP_TIMER_INTERVAL; |
|
|
|
|
uint64_t discovery_remaining = 5000; |
|
|
|
|
void lwIP::lwip_loop(SocketTap *tap) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
uint64_t prev_tcp_time = 0, prev_status_time = 0, prev_discovery_time = 0; |
|
|
|
|
while(tap->_run) |
|
|
|
|
{ |
|
|
|
|
uint64_t now = OSUtils::now(); |
|
|
|
|
uint64_t since_tcp = now - prev_tcp_time; |
|
|
|
|
uint64_t since_discovery = now - prev_discovery_time; |
|
|
|
|
uint64_t since_status = now - prev_status_time; |
|
|
|
|
uint64_t tcp_remaining = LWIP_TCP_TIMER_INTERVAL; |
|
|
|
|
uint64_t discovery_remaining = 5000; |
|
|
|
|
|
|
|
|
|
#if defined(LIBZT_IPV6) |
|
|
|
|
#define DISCOVERY_INTERVAL 1000 |
|
|
|
|
#define DISCOVERY_INTERVAL 1000 |
|
|
|
|
#elif defined(LIBZT_IPV4) |
|
|
|
|
#define DISCOVERY_INTERVAL ARP_TMR_INTERVAL |
|
|
|
|
#define DISCOVERY_INTERVAL ARP_TMR_INTERVAL |
|
|
|
|
#endif |
|
|
|
|
// Main TCP/ETHARP timer section
|
|
|
|
|
if (since_tcp >= LWIP_TCP_TIMER_INTERVAL) { |
|
|
|
|
prev_tcp_time = now; |
|
|
|
|
tcp_tmr(); |
|
|
|
|
}
|
|
|
|
|
else { |
|
|
|
|
tcp_remaining = LWIP_TCP_TIMER_INTERVAL - since_tcp; |
|
|
|
|
} |
|
|
|
|
if (since_discovery >= DISCOVERY_INTERVAL) { |
|
|
|
|
prev_discovery_time = now; |
|
|
|
|
// Main TCP/ETHARP timer section
|
|
|
|
|
if (since_tcp >= LWIP_TCP_TIMER_INTERVAL) { |
|
|
|
|
prev_tcp_time = now; |
|
|
|
|
tcp_tmr(); |
|
|
|
|
}
|
|
|
|
|
else { |
|
|
|
|
tcp_remaining = LWIP_TCP_TIMER_INTERVAL - since_tcp; |
|
|
|
|
} |
|
|
|
|
if (since_discovery >= DISCOVERY_INTERVAL) { |
|
|
|
|
prev_discovery_time = now; |
|
|
|
|
#if defined(LIBZT_IPV4) |
|
|
|
|
etharp_tmr(); |
|
|
|
|
etharp_tmr(); |
|
|
|
|
#endif |
|
|
|
|
#if defined(LIBZT_IPV6) |
|
|
|
|
nd6_tmr(); |
|
|
|
|
nd6_tmr(); |
|
|
|
|
#endif |
|
|
|
|
} else { |
|
|
|
|
discovery_remaining = DISCOVERY_INTERVAL - since_discovery; |
|
|
|
|
} |
|
|
|
|
tap->_phy.poll((unsigned long)std::min(tcp_remaining,discovery_remaining)); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} else { |
|
|
|
|
discovery_remaining = DISCOVERY_INTERVAL - since_discovery; |
|
|
|
|
} |
|
|
|
|
tap->_phy.poll((unsigned long)std::min(tcp_remaining,discovery_remaining)); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void lwIP::lwip_rx(SocketTap *tap, const MAC &from,const MAC &to,unsigned int etherType,const void *data,unsigned int len) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
struct pbuf *p,*q; |
|
|
|
|
if (!tap->_enabled) |
|
|
|
|
return; |
|
|
|
|
struct eth_hdr ethhdr; |
|
|
|
|
from.copyTo(ethhdr.src.addr, 6); |
|
|
|
|
to.copyTo(ethhdr.dest.addr, 6); |
|
|
|
|
ethhdr.type = ZeroTier::Utils::hton((uint16_t)etherType); |
|
|
|
|
void lwIP::lwip_rx(SocketTap *tap, const MAC &from,const MAC &to,unsigned int etherType,const void *data,unsigned int len) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
struct pbuf *p,*q; |
|
|
|
|
if (!tap->_enabled) |
|
|
|
|
return; |
|
|
|
|
struct eth_hdr ethhdr; |
|
|
|
|
from.copyTo(ethhdr.src.addr, 6); |
|
|
|
|
to.copyTo(ethhdr.dest.addr, 6); |
|
|
|
|
ethhdr.type = ZeroTier::Utils::hton((uint16_t)etherType); |
|
|
|
|
|
|
|
|
|
p = pbuf_alloc(PBUF_RAW, len+sizeof(struct eth_hdr), PBUF_POOL); |
|
|
|
|
if (p != NULL) { |
|
|
|
|
const char *dataptr = reinterpret_cast<const char *>(data); |
|
|
|
|
// First pbuf gets ethernet header at start
|
|
|
|
|
q = p; |
|
|
|
|
if (q->len < sizeof(ethhdr)) { |
|
|
|
|
DEBUG_ERROR("dropped packet: first pbuf smaller than ethernet header"); |
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
memcpy(q->payload,ðhdr,sizeof(ethhdr)); |
|
|
|
|
memcpy((char*)q->payload + sizeof(ethhdr),dataptr,q->len - sizeof(ethhdr)); |
|
|
|
|
dataptr += q->len - sizeof(ethhdr); |
|
|
|
|
p = pbuf_alloc(PBUF_RAW, len+sizeof(struct eth_hdr), PBUF_POOL); |
|
|
|
|
if (p != NULL) { |
|
|
|
|
const char *dataptr = reinterpret_cast<const char *>(data); |
|
|
|
|
// First pbuf gets ethernet header at start
|
|
|
|
|
q = p; |
|
|
|
|
if (q->len < sizeof(ethhdr)) { |
|
|
|
|
DEBUG_ERROR("dropped packet: first pbuf smaller than ethernet header"); |
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
memcpy(q->payload,ðhdr,sizeof(ethhdr)); |
|
|
|
|
memcpy((char*)q->payload + sizeof(ethhdr),dataptr,q->len - sizeof(ethhdr)); |
|
|
|
|
dataptr += q->len - sizeof(ethhdr); |
|
|
|
|
|
|
|
|
|
// Remaining pbufs (if any) get rest of data
|
|
|
|
|
while ((q = q->next)) { |
|
|
|
|
memcpy(q->payload,dataptr,q->len); |
|
|
|
|
dataptr += q->len; |
|
|
|
|
} |
|
|
|
|
}
|
|
|
|
|
else { |
|
|
|
|
DEBUG_ERROR("dropped packet: no pbufs available"); |
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
{ |
|
|
|
|
// Remaining pbufs (if any) get rest of data
|
|
|
|
|
while ((q = q->next)) { |
|
|
|
|
memcpy(q->payload,dataptr,q->len); |
|
|
|
|
dataptr += q->len; |
|
|
|
|
} |
|
|
|
|
}
|
|
|
|
|
else { |
|
|
|
|
DEBUG_ERROR("dropped packet: no pbufs available"); |
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
{ |
|
|
|
|
#if defined(LIBZT_IPV6) |
|
|
|
|
if(tap->lwipdev6.input(p, &(tap->lwipdev6)) != ERR_OK) { |
|
|
|
|
DEBUG_ERROR("error while feeding frame into stack lwipdev6"); |
|
|
|
|
} |
|
|
|
|
if(tap->lwipdev6.input(p, &(tap->lwipdev6)) != ERR_OK) { |
|
|
|
|
DEBUG_ERROR("error while feeding frame into stack lwipdev6"); |
|
|
|
|
} |
|
|
|
|
#endif |
|
|
|
|
#if defined(LIBZT_IPV4) |
|
|
|
|
if(tap->lwipdev.input(p, &(tap->lwipdev)) != ERR_OK) { |
|
|
|
|
DEBUG_ERROR("error while feeding frame into stack lwipdev"); |
|
|
|
|
} |
|
|
|
|
if(tap->lwipdev.input(p, &(tap->lwipdev)) != ERR_OK) { |
|
|
|
|
DEBUG_ERROR("error while feeding frame into stack lwipdev"); |
|
|
|
|
} |
|
|
|
|
#endif |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Socket(void **pcb, int socket_family, int socket_type, int protocol) |
|
|
|
|
{ |
|
|
|
|
// TODO: check lwIP timers, and max sockets
|
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
if(socket_type == SOCK_STREAM) { |
|
|
|
|
struct tcp_pcb *new_tcp_PCB = tcp_new(); |
|
|
|
|
*pcb = new_tcp_PCB; |
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
if(socket_type == SOCK_DGRAM) { |
|
|
|
|
struct udp_pcb *new_udp_PCB = udp_new(); |
|
|
|
|
*pcb = new_udp_PCB; |
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
if(socket_type == SOCK_RAW) { |
|
|
|
|
DEBUG_ERROR("SOCK_RAW, not currently supported."); |
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
int lwIP::lwip_Socket(void **pcb, int socket_family, int socket_type, int protocol) |
|
|
|
|
{ |
|
|
|
|
// TODO: check lwIP timers, and max sockets
|
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
if(socket_type == SOCK_STREAM) { |
|
|
|
|
struct tcp_pcb *new_tcp_PCB = tcp_new(); |
|
|
|
|
*pcb = new_tcp_PCB; |
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
if(socket_type == SOCK_DGRAM) { |
|
|
|
|
struct udp_pcb *new_udp_PCB = udp_new(); |
|
|
|
|
*pcb = new_udp_PCB; |
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
if(socket_type == SOCK_RAW) { |
|
|
|
|
DEBUG_ERROR("SOCK_RAW, not currently supported."); |
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Connect(Connection *conn, int fd, const struct sockaddr *addr, socklen_t addrlen) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
} |
|
|
|
|
int lwIP::lwip_Connect(Connection *conn, int fd, const struct sockaddr *addr, socklen_t addrlen) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Bind(SocketTap *tap, Connection *conn, int fd, const struct sockaddr *addr, socklen_t addrlen) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
ip_addr_t ba; |
|
|
|
|
char addrstr[INET6_ADDRSTRLEN]; |
|
|
|
|
int port = 0, err = 0; |
|
|
|
|
int lwIP::lwip_Bind(SocketTap *tap, Connection *conn, int fd, const struct sockaddr *addr, socklen_t addrlen) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
ip_addr_t ba; |
|
|
|
|
char addrstr[INET6_ADDRSTRLEN]; |
|
|
|
|
int port = 0, err = 0; |
|
|
|
|
|
|
|
|
|
#if defined(LIBZT_IPV4) |
|
|
|
|
DEBUG_ERROR("A"); |
|
|
|
|
struct sockaddr_in *in4; |
|
|
|
|
if(addr->sa_family == AF_INET) { |
|
|
|
|
DEBUG_ERROR("A"); |
|
|
|
|
in4 = (struct sockaddr_in *)addr; |
|
|
|
|
DEBUG_ERROR("A"); |
|
|
|
|
inet_ntop(AF_INET, &(in4->sin_addr), addrstr, INET_ADDRSTRLEN);
|
|
|
|
|
DEBUG_ERROR("A");
|
|
|
|
|
DEBUG_INFO("%s:%d", addrstr, lwip_ntohs(in4->sin_port)); |
|
|
|
|
} |
|
|
|
|
ba = convert_ip(in4);
|
|
|
|
|
port = lwip_ntohs(in4->sin_port); |
|
|
|
|
DEBUG_INFO("port=%d", port); |
|
|
|
|
DEBUG_INFO("port=%d", lwip_ntohs(port)); |
|
|
|
|
DEBUG_ERROR("A"); |
|
|
|
|
struct sockaddr_in *in4; |
|
|
|
|
if(addr->sa_family == AF_INET) { |
|
|
|
|
DEBUG_ERROR("A"); |
|
|
|
|
in4 = (struct sockaddr_in *)addr; |
|
|
|
|
DEBUG_ERROR("A"); |
|
|
|
|
inet_ntop(AF_INET, &(in4->sin_addr), addrstr, INET_ADDRSTRLEN);
|
|
|
|
|
DEBUG_ERROR("A");
|
|
|
|
|
DEBUG_INFO("%s:%d", addrstr, lwip_ntohs(in4->sin_port)); |
|
|
|
|
} |
|
|
|
|
ba = convert_ip(in4);
|
|
|
|
|
port = lwip_ntohs(in4->sin_port); |
|
|
|
|
DEBUG_INFO("port=%d", port); |
|
|
|
|
DEBUG_INFO("port=%d", lwip_ntohs(port)); |
|
|
|
|
#endif |
|
|
|
|
#if defined(LIBZT_IPV6) |
|
|
|
|
struct sockaddr_in6 *in6 = (struct sockaddr_in6*)&addr; |
|
|
|
|
in6_to_ip6((ip6_addr *)&ba, in6); |
|
|
|
|
if(addr->sa_family == AF_INET6) {
|
|
|
|
|
struct sockaddr_in6 *connaddr6 = (struct sockaddr_in6 *)addr; |
|
|
|
|
inet_ntop(AF_INET6, &(connaddr6->sin6_addr), addrstr, INET6_ADDRSTRLEN); |
|
|
|
|
DEBUG_INFO("%s:%d", addrstr, lwip_ntohs(connaddr6->sin6_port)); |
|
|
|
|
} |
|
|
|
|
struct sockaddr_in6 *in6 = (struct sockaddr_in6*)&addr; |
|
|
|
|
in6_to_ip6((ip6_addr *)&ba, in6); |
|
|
|
|
if(addr->sa_family == AF_INET6) {
|
|
|
|
|
struct sockaddr_in6 *connaddr6 = (struct sockaddr_in6 *)addr; |
|
|
|
|
inet_ntop(AF_INET6, &(connaddr6->sin6_addr), addrstr, INET6_ADDRSTRLEN); |
|
|
|
|
DEBUG_INFO("%s:%d", addrstr, lwip_ntohs(connaddr6->sin6_port)); |
|
|
|
|
} |
|
|
|
|
#endif |
|
|
|
|
if(conn->socket_type == SOCK_DGRAM) { |
|
|
|
|
err = udp_bind((struct udp_pcb*)conn->pcb, (const ip_addr_t *)&ba, port); |
|
|
|
|
if(err == ERR_USE) { |
|
|
|
|
err = -1; |
|
|
|
|
errno = EADDRINUSE; // port in use
|
|
|
|
|
} |
|
|
|
|
else { |
|
|
|
|
// set the recv callback
|
|
|
|
|
udp_recv((struct udp_pcb*)conn->pcb, nc_udp_recved, new ConnectionPair(tap, conn)); |
|
|
|
|
err = ERR_OK;
|
|
|
|
|
errno = ERR_OK; // success
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
else if (conn->socket_type == SOCK_STREAM) { |
|
|
|
|
err = tcp_bind((struct tcp_pcb*)conn->pcb, (const ip_addr_t *)&ba, port); |
|
|
|
|
if(err != ERR_OK) { |
|
|
|
|
DEBUG_ERROR("err=%d", err); |
|
|
|
|
if(err == ERR_USE){ |
|
|
|
|
err = -1;
|
|
|
|
|
errno = EADDRINUSE; |
|
|
|
|
} |
|
|
|
|
if(err == ERR_MEM){ |
|
|
|
|
err = -1;
|
|
|
|
|
errno = ENOMEM; |
|
|
|
|
} |
|
|
|
|
if(err == ERR_BUF){ |
|
|
|
|
err = -1;
|
|
|
|
|
errno = ENOMEM; |
|
|
|
|
} |
|
|
|
|
}
|
|
|
|
|
else { |
|
|
|
|
err = ERR_OK;
|
|
|
|
|
errno = ERR_OK; // success
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
return err; |
|
|
|
|
} |
|
|
|
|
if(conn->socket_type == SOCK_DGRAM) { |
|
|
|
|
err = udp_bind((struct udp_pcb*)conn->pcb, (const ip_addr_t *)&ba, port); |
|
|
|
|
if(err == ERR_USE) { |
|
|
|
|
err = -1; |
|
|
|
|
errno = EADDRINUSE; // port in use
|
|
|
|
|
} |
|
|
|
|
else { |
|
|
|
|
// set the recv callback
|
|
|
|
|
udp_recv((struct udp_pcb*)conn->pcb, nc_udp_recved, new ConnectionPair(tap, conn)); |
|
|
|
|
err = ERR_OK;
|
|
|
|
|
errno = ERR_OK; // success
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
else if (conn->socket_type == SOCK_STREAM) { |
|
|
|
|
err = tcp_bind((struct tcp_pcb*)conn->pcb, (const ip_addr_t *)&ba, port); |
|
|
|
|
if(err != ERR_OK) { |
|
|
|
|
DEBUG_ERROR("err=%d", err); |
|
|
|
|
if(err == ERR_USE){ |
|
|
|
|
err = -1;
|
|
|
|
|
errno = EADDRINUSE; |
|
|
|
|
} |
|
|
|
|
if(err == ERR_MEM){ |
|
|
|
|
err = -1;
|
|
|
|
|
errno = ENOMEM; |
|
|
|
|
} |
|
|
|
|
if(err == ERR_BUF){ |
|
|
|
|
err = -1;
|
|
|
|
|
errno = ENOMEM; |
|
|
|
|
} |
|
|
|
|
}
|
|
|
|
|
else { |
|
|
|
|
err = ERR_OK;
|
|
|
|
|
errno = ERR_OK; // success
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
return err; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Listen(SocketTap *tap, PhySocket *sock, PhySocket *rpcSock, void **uptr, struct listen_st *listen_rpc) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
int lwIP::lwip_Listen(SocketTap *tap, PhySocket *sock, PhySocket *rpcSock, void **uptr, struct listen_st *listen_rpc) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Read(SocketTap *tap, PhySocket *sock, void **uptr, bool lwip_invoked) |
|
|
|
|
{ |
|
|
|
|
DEBUG_EXTRA(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
int lwIP::lwip_Read(SocketTap *tap, PhySocket *sock, void **uptr, bool lwip_invoked) |
|
|
|
|
{ |
|
|
|
|
DEBUG_EXTRA(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Write(SocketTap *tap, Connection *conn) |
|
|
|
|
{ |
|
|
|
|
DEBUG_EXTRA("conn=%p", (void*)&conn); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
int lwIP::lwip_Write(SocketTap *tap, Connection *conn) |
|
|
|
|
{ |
|
|
|
|
DEBUG_EXTRA("conn=%p", (void*)&conn); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
int lwIP::lwip_Close(SocketTap *tap, PhySocket *sock, Connection *conn) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
int lwIP::lwip_Close(SocketTap *tap, PhySocket *sock, Connection *conn) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/****************************************************************************/ |
|
|
|
|
/* Callbacks from lwIP stack */ |
|
|
|
|
/****************************************************************************/ |
|
|
|
|
/****************************************************************************/ |
|
|
|
|
/* Callbacks from lwIP stack */ |
|
|
|
|
/****************************************************************************/ |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_recved(void *arg, struct tcp_pcb *PCB, struct pbuf *p, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
err_t lwIP::nc_recved(void *arg, struct tcp_pcb *PCB, struct pbuf *p, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_accept(void *arg, struct tcp_pcb *newPCB, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void lwIP::nc_udp_recved(void * arg, struct udp_pcb * upcb, struct pbuf * p, const ip_addr_t * addr, u16_t port) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_sent(void* arg, struct tcp_pcb *PCB, u16_t len) |
|
|
|
|
{ |
|
|
|
|
DEBUG_EXTRA("pcb=%p", (void*)&PCB); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_connected(void *arg, struct tcp_pcb *PCB, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_ATTN("pcb=%p", (void*)&PCB); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
err_t lwIP::nc_accept(void *arg, struct tcp_pcb *newPCB, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
return -1; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void lwIP::nc_udp_recved(void * arg, struct udp_pcb * upcb, struct pbuf * p, const ip_addr_t * addr, u16_t port) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_sent(void* arg, struct tcp_pcb *PCB, u16_t len) |
|
|
|
|
{ |
|
|
|
|
DEBUG_EXTRA("pcb=%p", (void*)&PCB); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_connected(void *arg, struct tcp_pcb *PCB, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_ATTN("pcb=%p", (void*)&PCB); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
err_t lwIP::nc_poll(void* arg, struct tcp_pcb *PCB) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
err_t lwIP::nc_poll(void* arg, struct tcp_pcb *PCB) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
return ERR_OK; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
void lwIP::nc_err(void *arg, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
void lwIP::nc_err(void *arg, err_t err) |
|
|
|
|
{ |
|
|
|
|
DEBUG_INFO(); |
|
|
|
|
// to be implemented
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|