diff options
-rw-r--r-- | bootp.c | 25 | ||||
-rw-r--r-- | ctl.h | 7 | ||||
-rw-r--r-- | ip_icmp.c | 16 | ||||
-rw-r--r-- | ip_input.c | 9 | ||||
-rw-r--r-- | main.h | 9 | ||||
-rw-r--r-- | misc.c | 6 | ||||
-rw-r--r-- | misc.h | 4 | ||||
-rw-r--r-- | slirp.c | 123 | ||||
-rw-r--r-- | slirp.h | 1 | ||||
-rw-r--r-- | socket.c | 12 | ||||
-rw-r--r-- | tcp_input.c | 16 | ||||
-rw-r--r-- | tcp_subr.c | 18 | ||||
-rw-r--r-- | udp.c | 22 |
13 files changed, 135 insertions, 133 deletions
@@ -27,8 +27,6 @@ #define NB_ADDR 16 -#define START_ADDR 15 - #define LEASE_TIME (24 * 3600) typedef struct { @@ -66,7 +64,7 @@ static BOOTPClient *get_new_addr(struct in_addr *paddr, const uint8_t *macaddr) found: bc = &bootp_clients[i]; bc->allocated = 1; - paddr->s_addr = htonl(ntohl(special_addr.s_addr) | (i + START_ADDR)); + paddr->s_addr = vdhcp_startaddr.s_addr + htonl(i); return bc; } @@ -74,12 +72,11 @@ static BOOTPClient *request_addr(const struct in_addr *paddr, const uint8_t *macaddr) { uint32_t req_addr = ntohl(paddr->s_addr); - uint32_t spec_addr = ntohl(special_addr.s_addr); + uint32_t dhcp_addr = ntohl(vdhcp_startaddr.s_addr); BOOTPClient *bc; - if (req_addr >= (spec_addr | START_ADDR) && - req_addr < (spec_addr | (NB_ADDR + START_ADDR))) { - bc = &bootp_clients[(req_addr & 0xff) - START_ADDR]; + if (req_addr >= dhcp_addr && req_addr < (dhcp_addr + NB_ADDR)) { + bc = &bootp_clients[req_addr - dhcp_addr]; if (!bc->allocated || !memcmp(macaddr, bc->macaddr, 6)) { bc->allocated = 1; return bc; @@ -101,7 +98,7 @@ static BOOTPClient *find_addr(struct in_addr *paddr, const uint8_t *macaddr) found: bc = &bootp_clients[i]; bc->allocated = 1; - paddr->s_addr = htonl(ntohl(special_addr.s_addr) | (i + START_ADDR)); + paddr->s_addr = vdhcp_startaddr.s_addr + htonl(i); return bc; } @@ -158,7 +155,6 @@ static void bootp_reply(const struct bootp_t *bp) struct mbuf *m; struct bootp_t *rbp; struct sockaddr_in saddr, daddr; - struct in_addr dns_addr; const struct in_addr *preq_addr; int dhcp_msg_type, val; uint8_t *q; @@ -219,7 +215,7 @@ static void bootp_reply(const struct bootp_t *bp) } } - saddr.sin_addr.s_addr = htonl(ntohl(special_addr.s_addr) | CTL_ALIAS); + saddr.sin_addr = vhost_addr; saddr.sin_port = htons(BOOTP_SERVER); daddr.sin_port = htons(BOOTP_CLIENT); @@ -263,10 +259,8 @@ static void bootp_reply(const struct bootp_t *bp) *q++ = RFC1533_NETMASK; *q++ = 4; - *q++ = 0xff; - *q++ = 0xff; - *q++ = 0xff; - *q++ = 0x00; + memcpy(q, &vnetwork_mask, 4); + q += 4; if (!slirp_restrict) { *q++ = RFC1533_GATEWAY; @@ -276,8 +270,7 @@ static void bootp_reply(const struct bootp_t *bp) *q++ = RFC1533_DNS; *q++ = 4; - dns_addr.s_addr = htonl(ntohl(special_addr.s_addr) | CTL_DNS); - memcpy(q, &dns_addr, 4); + memcpy(q, &vnameserver_addr, 4); q += 4; } @@ -1,7 +0,0 @@ -#define CTL_CMD 0 -#define CTL_EXEC 1 -#define CTL_ALIAS 2 -#define CTL_DNS 3 - -#define CTL_SPECIAL "10.0.2.0" -#define CTL_LOCAL "10.0.2.15" @@ -111,7 +111,7 @@ void icmp_input(struct mbuf *m, int hlen) case ICMP_ECHO: icp->icmp_type = ICMP_ECHOREPLY; ip->ip_len += hlen; /* since ip_input subtracts this */ - if (ip->ip_dst.s_addr == alias_addr.s_addr) { + if (ip->ip_dst.s_addr == vhost_addr.s_addr) { icmp_reflect(m); } else { struct socket *so; @@ -136,17 +136,13 @@ void icmp_input(struct mbuf *m, int hlen) /* Send the packet */ addr.sin_family = AF_INET; - if ((so->so_faddr.s_addr & htonl(0xffffff00)) == - special_addr.s_addr) { + if ((so->so_faddr.s_addr & vnetwork_mask.s_addr) == + vnetwork_addr.s_addr) { /* It's an alias */ - switch (ntohl(so->so_faddr.s_addr) & 0xff) { - case CTL_DNS: + if (so->so_faddr.s_addr == vnameserver_addr.s_addr) { addr.sin_addr = dns_addr; - break; - case CTL_ALIAS: - default: + } else { addr.sin_addr = loopback_addr; - break; } } else { addr.sin_addr = so->so_faddr; @@ -315,7 +311,7 @@ void icmp_error(struct mbuf *msrc, u_char type, u_char code, int minsize, ip->ip_ttl = MAXTTL; ip->ip_p = IPPROTO_ICMP; ip->ip_dst = ip->ip_src; /* ip adresses */ - ip->ip_src = alias_addr; + ip->ip_src = vhost_addr; (void)ip_output((struct socket *)NULL, m); @@ -130,18 +130,19 @@ void ip_input(struct mbuf *m) } if (slirp_restrict) { - if (memcmp(&ip->ip_dst.s_addr, &special_addr, 3)) { + if ((ip->ip_dst.s_addr & vnetwork_mask.s_addr) == + vnetwork_addr.s_addr) { if (ip->ip_dst.s_addr == 0xffffffff && ip->ip_p != IPPROTO_UDP) goto bad; } else { - int host = ntohl(ip->ip_dst.s_addr) & 0xff; struct ex_list *ex_ptr; - if (host == 0xff) + if ((ip->ip_dst.s_addr & ~vnetwork_mask.s_addr) == + ~vnetwork_mask.s_addr) goto bad; for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) - if (ex_ptr->ex_addr == host) + if (ex_ptr->ex_addr.s_addr == ip->ip_dst.s_addr) break; if (!ex_ptr) @@ -32,9 +32,11 @@ extern char *slirp_tty; extern char *exec_shell; extern u_int curtime; extern fd_set *global_readfds, *global_writefds, *global_xfds; -extern struct in_addr ctl_addr; -extern struct in_addr special_addr; -extern struct in_addr alias_addr; +extern struct in_addr vnetwork_addr; +extern struct in_addr vnetwork_mask; +extern struct in_addr vhost_addr; +extern struct in_addr vdhcp_startaddr; +extern struct in_addr vnameserver_addr; extern struct in_addr our_addr; extern struct in_addr loopback_addr; extern struct in_addr dns_addr; @@ -44,7 +46,6 @@ extern int towrite_max; extern int ppp_exit; extern int tcp_keepintvl; extern uint8_t client_ethaddr[6]; -extern const char *slirp_special_ip; extern int slirp_restrict; extern char *tftp_prefix; extern char *bootp_filename; @@ -109,14 +109,14 @@ inline void remque(void *a) /* #endif */ -int add_exec(struct ex_list **ex_ptr, int do_pty, char *exec, int addr, - int port) +int add_exec(struct ex_list **ex_ptr, int do_pty, char *exec, + struct in_addr addr, int port) { struct ex_list *tmp_ptr; /* First, check if the port is "bound" */ for (tmp_ptr = *ex_ptr; tmp_ptr; tmp_ptr = tmp_ptr->ex_next) { - if (port == tmp_ptr->ex_fport && addr == tmp_ptr->ex_addr) + if (port == tmp_ptr->ex_fport && addr.s_addr == tmp_ptr->ex_addr.s_addr) return -1; } @@ -10,7 +10,7 @@ struct ex_list { int ex_pty; /* Do we want a pty? */ - int ex_addr; /* The last byte of the address */ + struct in_addr ex_addr; /* Server address */ int ex_fport; /* Port to telnet to */ const char *ex_exec; /* Command line of what to exec */ struct ex_list *ex_next; @@ -74,7 +74,7 @@ void redir_x _P((u_int32_t, int, int, int)); void getouraddr _P((void)); void slirp_insque _P((void *, void *)); void slirp_remque _P((void *)); -int add_exec _P((struct ex_list **, int, char *, int, int)); +int add_exec _P((struct ex_list **, int, char *, struct in_addr, int)); int slirp_openpty _P((int *, int *)); int fork_exec(struct socket *so, const char *ex, int do_pty); void snooze_hup _P((int)); @@ -33,13 +33,16 @@ struct in_addr dns_addr; /* host loopback address */ struct in_addr loopback_addr; -/* address for slirp virtual addresses */ -struct in_addr special_addr; -/* virtual address alias for host */ -struct in_addr alias_addr; - +/* virtual network configuration */ +struct in_addr vnetwork_addr; +struct in_addr vnetwork_mask; +struct in_addr vhost_addr; +struct in_addr vdhcp_startaddr; +struct in_addr vnameserver_addr; + +/* emulated hosts use the MAC addr 52:55:IP:IP:IP:IP */ static const uint8_t special_ethaddr[6] = { - 0x52, 0x54, 0x00, 0x12, 0x35, 0x00 + 0x52, 0x55, 0x00, 0x00, 0x00, 0x00 }; /* ARP cache for the guest IP addresses (XXX: allow many entries) */ @@ -48,7 +51,6 @@ static struct in_addr client_ipaddr; static const uint8_t zero_ethaddr[6] = { 0, 0, 0, 0, 0, 0 }; -const char *slirp_special_ip = CTL_SPECIAL; int slirp_restrict; static int do_slowtimo; int link_up; @@ -176,12 +178,12 @@ void slirp_init(int restricted, const char *special_ip, const char *tftp_path, { // debug_init("/tmp/slirp.log", DEBUG_DEFAULT); + struct in_addr special_addr = { .s_addr = htonl(0x0a000200) }; #ifdef _WIN32 - { - WSADATA Data; - WSAStartup(MAKEWORD(2, 0), &Data); - atexit(slirp_cleanup); - } + WSADATA Data; + + WSAStartup(MAKEWORD(2, 0), &Data); + atexit(slirp_cleanup); #endif link_up = 1; @@ -201,9 +203,9 @@ void slirp_init(int restricted, const char *special_ip, const char *tftp_path, fprintf(stderr, "Warning: No DNS servers found\n"); } - if (special_ip) - slirp_special_ip = special_ip; - + if (special_ip) { + inet_aton(special_ip, &special_addr); + } qemu_free(tftp_prefix); tftp_prefix = NULL; if (tftp_path) { @@ -215,8 +217,11 @@ void slirp_init(int restricted, const char *special_ip, const char *tftp_path, bootp_filename = qemu_strdup(bootfile); } - inet_aton(slirp_special_ip, &special_addr); - alias_addr.s_addr = special_addr.s_addr | htonl(CTL_ALIAS); + vnetwork_addr = special_addr; + vnetwork_mask.s_addr = htonl(0xffffff00); + vhost_addr.s_addr = special_addr.s_addr | htonl(2); + vdhcp_startaddr.s_addr = special_addr.s_addr | htonl(15); + vnameserver_addr.s_addr = special_addr.s_addr | htonl(3); getouraddr(); register_savevm("slirp", 0, 1, slirp_state_save, slirp_state_load, NULL); } @@ -603,10 +608,10 @@ struct arphdr { * Ethernet looks like this : This bit is variable sized however... */ unsigned char ar_sha[ETH_ALEN]; /* sender hardware address */ - unsigned char ar_sip[4]; /* sender IP address */ + uint32_t ar_sip; /* sender IP address */ unsigned char ar_tha[ETH_ALEN]; /* target hardware address */ - unsigned char ar_tip[4]; /* target IP address */ -}; + uint32_t ar_tip; /* target IP address */ +} __attribute__((packed)); static void arp_input(const uint8_t *pkt, int pkt_len) { @@ -621,11 +626,12 @@ static void arp_input(const uint8_t *pkt, int pkt_len) ar_op = ntohs(ah->ar_op); switch (ar_op) { case ARPOP_REQUEST: - if (!memcmp(ah->ar_tip, &special_addr, 3)) { - if (ah->ar_tip[3] == CTL_DNS || ah->ar_tip[3] == CTL_ALIAS) + if ((ah->ar_tip & vnetwork_mask.s_addr) == vnetwork_addr.s_addr) { + if (ah->ar_tip == vnameserver_addr.s_addr || + ah->ar_tip == vhost_addr.s_addr) goto arp_ok; for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) { - if (ex_ptr->ex_addr == ah->ar_tip[3]) + if (ex_ptr->ex_addr.s_addr == ah->ar_tip) goto arp_ok; } return; @@ -635,8 +641,8 @@ static void arp_input(const uint8_t *pkt, int pkt_len) /* ARP request for alias/dns mac address */ memcpy(reh->h_dest, pkt + ETH_ALEN, ETH_ALEN); - memcpy(reh->h_source, special_ethaddr, ETH_ALEN - 1); - reh->h_source[5] = ah->ar_tip[3]; + memcpy(reh->h_source, special_ethaddr, ETH_ALEN - 4); + memcpy(&reh->h_source[2], &ah->ar_tip, 4); reh->h_proto = htons(ETH_P_ARP); rah->ar_hrd = htons(1); @@ -645,16 +651,16 @@ static void arp_input(const uint8_t *pkt, int pkt_len) rah->ar_pln = 4; rah->ar_op = htons(ARPOP_REPLY); memcpy(rah->ar_sha, reh->h_source, ETH_ALEN); - memcpy(rah->ar_sip, ah->ar_tip, 4); + rah->ar_sip = ah->ar_tip; memcpy(rah->ar_tha, ah->ar_sha, ETH_ALEN); - memcpy(rah->ar_tip, ah->ar_sip, 4); + rah->ar_tip = ah->ar_sip; slirp_output(arp_reply, sizeof(arp_reply)); } break; case ARPOP_REPLY: /* reply to request of client mac address ? */ if (!memcmp(client_ethaddr, zero_ethaddr, ETH_ALEN) && - !memcmp(ah->ar_sip, &client_ipaddr.s_addr, 4)) { + ah->ar_sip == client_ipaddr.s_addr) { memcpy(client_ethaddr, ah->ar_sha, ETH_ALEN); } break; @@ -718,8 +724,8 @@ void if_encap(const uint8_t *ip_data, int ip_data_len) in place of sending the packet and we hope that the sender will retry sending its packet. */ memset(reh->h_dest, 0xff, ETH_ALEN); - memcpy(reh->h_source, special_ethaddr, ETH_ALEN - 1); - reh->h_source[5] = CTL_ALIAS; + memcpy(reh->h_source, special_ethaddr, ETH_ALEN - 4); + memcpy(&reh->h_source[2], &vhost_addr, 4); reh->h_proto = htons(ETH_P_ARP); rah->ar_hrd = htons(1); rah->ar_pro = htons(ETH_P_IP); @@ -727,21 +733,21 @@ void if_encap(const uint8_t *ip_data, int ip_data_len) rah->ar_pln = 4; rah->ar_op = htons(ARPOP_REQUEST); /* source hw addr */ - memcpy(rah->ar_sha, special_ethaddr, ETH_ALEN - 1); - rah->ar_sha[5] = CTL_ALIAS; + memcpy(rah->ar_sha, special_ethaddr, ETH_ALEN - 4); + memcpy(&rah->ar_sha[2], &vhost_addr, 4); /* source IP */ - memcpy(rah->ar_sip, &alias_addr, 4); + rah->ar_sip = vhost_addr.s_addr; /* target hw addr (none) */ memset(rah->ar_tha, 0, ETH_ALEN); /* target IP */ - memcpy(rah->ar_tip, &iph->ip_dst, 4); + rah->ar_tip = iph->ip_dst.s_addr; client_ipaddr = iph->ip_dst; slirp_output(arp_req, sizeof(arp_req)); } else { memcpy(eh->h_dest, client_ethaddr, ETH_ALEN); - memcpy(eh->h_source, special_ethaddr, ETH_ALEN - 1); + memcpy(eh->h_source, special_ethaddr, ETH_ALEN - 4); /* XXX: not correct */ - eh->h_source[5] = CTL_ALIAS; + memcpy(&eh->h_source[2], &vhost_addr, 4); eh->h_proto = htons(ETH_P_IP); memcpy(buf + sizeof(struct ethhdr), ip_data, ip_data_len); slirp_output(buf, ip_data_len + ETH_HLEN); @@ -774,6 +780,9 @@ loop_again: int slirp_redir(int is_udp, int host_port, struct in_addr guest_addr, int guest_port) { + if (!guest_addr.s_addr) { + guest_addr = vdhcp_startaddr; + } if (is_udp) { if (!udp_listen(htons(host_port), guest_addr.s_addr, htons(guest_port), 0)) @@ -789,7 +798,15 @@ int slirp_redir(int is_udp, int host_port, struct in_addr guest_addr, int slirp_add_exec(int do_pty, const void *args, int addr_low_byte, int guest_port) { - return add_exec(&exec_list, do_pty, (char *)args, addr_low_byte, + struct in_addr guest_addr = { .s_addr = vnetwork_addr.s_addr | + htonl(addr_low_byte) }; + + if ((guest_addr.s_addr & vnetwork_mask.s_addr) != vnetwork_addr.s_addr || + guest_addr.s_addr == vhost_addr.s_addr || + guest_addr.s_addr == vnameserver_addr.s_addr) { + return -1; + } + return add_exec(&exec_list, do_pty, (char *)args, guest_addr, htons(guest_port)); } @@ -803,29 +820,31 @@ ssize_t slirp_send(struct socket *so, const void *buf, size_t len, int flags) return send(so->s, buf, len, flags); } -static struct socket *slirp_find_ctl_socket(int addr_low_byte, int guest_port) +static struct socket *slirp_find_ctl_socket(struct in_addr guest_addr, + int guest_port) { struct socket *so; for (so = tcb.so_next; so != &tcb; so = so->so_next) { - if ((so->so_faddr.s_addr & htonl(0xffffff00)) == special_addr.s_addr && - (ntohl(so->so_faddr.s_addr) & 0xff) == addr_low_byte && - htons(so->so_fport) == guest_port) + if (so->so_faddr.s_addr == guest_addr.s_addr && + htons(so->so_fport) == guest_port) { return so; + } } - return NULL; } size_t slirp_socket_can_recv(int addr_low_byte, int guest_port) { + struct in_addr guest_addr = { .s_addr = vnetwork_addr.s_addr | + htonl(addr_low_byte) }; struct iovec iov[2]; struct socket *so; if (!link_up) return 0; - so = slirp_find_ctl_socket(addr_low_byte, guest_port); + so = slirp_find_ctl_socket(guest_addr, guest_port); if (!so || so->so_state & SS_NOFDREF) return 0; @@ -840,7 +859,9 @@ void slirp_socket_recv(int addr_low_byte, int guest_port, const uint8_t *buf, int size) { int ret; - struct socket *so = slirp_find_ctl_socket(addr_low_byte, guest_port); + struct in_addr guest_addr = { .s_addr = vnetwork_addr.s_addr | + htonl(addr_low_byte) }; + struct socket *so = slirp_find_ctl_socket(guest_addr, guest_port); if (!so) return; @@ -1056,15 +1077,17 @@ static int slirp_state_load(QEMUFile *f, void *opaque, int version_id) if (ret < 0) return ret; - if ((so->so_faddr.s_addr & htonl(0xffffff00)) != special_addr.s_addr) + if ((so->so_faddr.s_addr & vnetwork_mask.s_addr) != + vnetwork_addr.s_addr) { return -EINVAL; - - for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) + } + for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) { if (ex_ptr->ex_pty == 3 && - (ntohl(so->so_faddr.s_addr) & 0xff) == ex_ptr->ex_addr && - so->so_fport == ex_ptr->ex_fport) + so->so_faddr.s_addr == ex_ptr->ex_addr.s_addr && + so->so_fport == ex_ptr->ex_fport) { break; - + } + } if (!ex_ptr) return -EINVAL; @@ -216,7 +216,6 @@ int inet_aton _P((const char *cp, struct in_addr *ia)); #include "if.h" #include "main.h" #include "misc.h" -#include "ctl.h" #ifdef USE_PPP #include "ppp/pppd.h" #include "ppp/ppp.h" @@ -561,16 +561,12 @@ int sosendto(struct socket *so, struct mbuf *m) DEBUG_ARG("m = %lx", (long)m); addr.sin_family = AF_INET; - if ((so->so_faddr.s_addr & htonl(0xffffff00)) == special_addr.s_addr) { + if ((so->so_faddr.s_addr & vnetwork_mask.s_addr) == vnetwork_addr.s_addr) { /* It's an alias */ - switch (ntohl(so->so_faddr.s_addr) & 0xff) { - case CTL_DNS: + if (so->so_faddr.s_addr == vnameserver_addr.s_addr) { addr.sin_addr = dns_addr; - break; - case CTL_ALIAS: - default: + } else { addr.sin_addr = loopback_addr; - break; } } else addr.sin_addr = so->so_faddr; @@ -661,7 +657,7 @@ struct socket *solisten(u_int port, u_int32_t laddr, u_int lport, int flags) so->so_fport = addr.sin_port; if (addr.sin_addr.s_addr == 0 || addr.sin_addr.s_addr == loopback_addr.s_addr) - so->so_faddr = alias_addr; + so->so_faddr = vhost_addr; else so->so_faddr = addr.sin_addr; diff --git a/tcp_input.c b/tcp_input.c index 383457f..2dcc703 100644 --- a/tcp_input.c +++ b/tcp_input.c @@ -360,11 +360,12 @@ void tcp_input(struct mbuf *m, int iphlen, struct socket *inso) m->m_len -= sizeof(struct tcpiphdr) + off - sizeof(struct tcphdr); if (slirp_restrict) { - for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) + for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) { if (ex_ptr->ex_fport == ti->ti_dport && - (ntohl(ti->ti_dst.s_addr) & 0xff) == ex_ptr->ex_addr) + ti->ti_dst.s_addr == ex_ptr->ex_addr.s_addr) { break; - + } + } if (!ex_ptr) goto drop; } @@ -636,9 +637,10 @@ findso: * If this is destined for the control address, then flag to * tcp_ctl once connected, otherwise connect */ - if ((so->so_faddr.s_addr & htonl(0xffffff00)) == special_addr.s_addr) { - int lastbyte = ntohl(so->so_faddr.s_addr) & 0xff; - if (lastbyte != CTL_ALIAS && lastbyte != CTL_DNS) { + if ((so->so_faddr.s_addr & vnetwork_mask.s_addr) == + vnetwork_addr.s_addr) { + if (so->so_faddr.s_addr != vhost_addr.s_addr && + so->so_faddr.s_addr != vnameserver_addr.s_addr) { #if 0 if(lastbyte==CTL_CMD || lastbyte==CTL_EXEC) { /* Command or exec adress */ @@ -649,7 +651,7 @@ findso: /* May be an add exec */ for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) { if (ex_ptr->ex_fport == so->so_fport && - lastbyte == ex_ptr->ex_addr) { + so->so_faddr.s_addr == ex_ptr->ex_addr.s_addr) { so->so_state |= SS_CTL; break; } @@ -380,16 +380,13 @@ int tcp_fconnect(struct socket *so) setsockopt(s, SOL_SOCKET, SO_OOBINLINE, (char *)&opt, sizeof(opt)); addr.sin_family = AF_INET; - if ((so->so_faddr.s_addr & htonl(0xffffff00)) == special_addr.s_addr) { + if ((so->so_faddr.s_addr & vnetwork_mask.s_addr) == + vnetwork_addr.s_addr) { /* It's an alias */ - switch (ntohl(so->so_faddr.s_addr) & 0xff) { - case CTL_DNS: + if (so->so_faddr.s_addr == vnameserver_addr.s_addr) { addr.sin_addr = dns_addr; - break; - case CTL_ALIAS: - default: + } else { addr.sin_addr = loopback_addr; - break; } } else addr.sin_addr = so->so_faddr; @@ -474,7 +471,7 @@ void tcp_connect(struct socket *inso) so->so_faddr = addr.sin_addr; /* Translate connections from localhost to the real hostname */ if (so->so_faddr.s_addr == 0 || so->so_faddr.s_addr == loopback_addr.s_addr) - so->so_faddr = alias_addr; + so->so_faddr = vhost_addr; /* Close the accept() socket, set right state */ if (inso->so_state & SS_FACCEPTONCE) { @@ -1232,7 +1229,6 @@ do_prompt: */ int tcp_ctl(struct socket *so) { - int command = (ntohl(so->so_faddr.s_addr) & 0xff); struct sbuf *sb = &so->so_snd; struct ex_list *ex_ptr; int do_pty; @@ -1240,11 +1236,11 @@ int tcp_ctl(struct socket *so) DEBUG_CALL("tcp_ctl"); DEBUG_ARG("so = %lx", (long)so); - if (command != CTL_ALIAS) { + if (so->so_faddr.s_addr != vhost_addr.s_addr) { /* Check if it's pty_exec */ for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) { if (ex_ptr->ex_fport == so->so_fport && - command == ex_ptr->ex_addr) { + so->so_faddr.s_addr == ex_ptr->ex_addr.s_addr) { if (ex_ptr->ex_pty == 3) { so->s = -1; so->extra = (void *)ex_ptr->ex_exec; @@ -312,12 +312,14 @@ int udp_output(struct socket *so, struct mbuf *m, struct sockaddr_in *addr) struct sockaddr_in saddr, daddr; saddr = *addr; - if ((so->so_faddr.s_addr & htonl(0xffffff00)) == special_addr.s_addr) { - if ((so->so_faddr.s_addr & htonl(0x000000ff)) == htonl(0xff)) - saddr.sin_addr.s_addr = alias_addr.s_addr; - else if (addr->sin_addr.s_addr == loopback_addr.s_addr || - (ntohl(so->so_faddr.s_addr) & 0xff) != CTL_ALIAS) - saddr.sin_addr.s_addr = so->so_faddr.s_addr; + if ((so->so_faddr.s_addr & vnetwork_mask.s_addr) == vnetwork_addr.s_addr) { + if ((so->so_faddr.s_addr & ~vnetwork_mask.s_addr) == + ~vnetwork_mask.s_addr) { + saddr.sin_addr = vhost_addr; + } else if (addr->sin_addr.s_addr == loopback_addr.s_addr || + so->so_faddr.s_addr != vhost_addr.s_addr) { + saddr.sin_addr = so->so_faddr; + } } daddr.sin_addr = so->so_laddr; daddr.sin_port = so->so_lport; @@ -647,11 +649,11 @@ struct socket *udp_listen(u_int port, u_int32_t laddr, u_int lport, int flags) getsockname(so->s, (struct sockaddr *)&addr, &addrlen); so->so_fport = addr.sin_port; if (addr.sin_addr.s_addr == 0 || - addr.sin_addr.s_addr == loopback_addr.s_addr) - so->so_faddr = alias_addr; - else + addr.sin_addr.s_addr == loopback_addr.s_addr) { + so->so_faddr = vhost_addr; + } else { so->so_faddr = addr.sin_addr; - + } so->so_lport = lport; so->so_laddr.s_addr = laddr; if (flags != SS_FACCEPTONCE) |