[f]truncate64 support
[qemu] / slirp / slirp.c
index bc2b155..3b840a8 100644 (file)
@@ -20,6 +20,7 @@ int do_slowtimo;
 int link_up;
 struct timeval tt;
 FILE *lfd;
+struct ex_list *exec_list;
 
 /* XXX: suppress those select globals */
 fd_set *global_readfds, *global_writefds, *global_xfds;
@@ -413,7 +414,7 @@ void slirp_select_poll(fd_set *readfds, fd_set *writefds, fd_set *xfds)
                            /* Connected */
                            so->so_state &= ~SS_ISFCONNECTING;
                            
-                           ret = write(so->s, &ret, 0);
+                           ret = send(so->s, &ret, 0, 0);
                            if (ret < 0) {
                              /* XXXXX Must fix, zero bytes is a NOP */
                              if (errno == EAGAIN || errno == EWOULDBLOCK ||
@@ -446,7 +447,7 @@ void slirp_select_poll(fd_set *readfds, fd_set *writefds, fd_set *xfds)
                         */
 #ifdef PROBE_CONN
                        if (so->so_state & SS_ISFCONNECTING) {
-                         ret = read(so->s, (char *)&ret, 0);
+                         ret = recv(so->s, (char *)&ret, 0,0);
                          
                          if (ret < 0) {
                            /* XXX */
@@ -459,7 +460,7 @@ void slirp_select_poll(fd_set *readfds, fd_set *writefds, fd_set *xfds)
                            
                            /* tcp_input will take care of it */
                          } else {
-                           ret = write(so->s, &ret, 0);
+                           ret = send(so->s, &ret, 0,0);
                            if (ret < 0) {
                              /* XXX */
                              if (errno == EAGAIN || errno == EWOULDBLOCK ||
@@ -495,6 +496,15 @@ void slirp_select_poll(fd_set *readfds, fd_set *writefds, fd_set *xfds)
         */
        if (if_queued && link_up)
           if_start();
+
+       /* clear global file descriptor sets.
+        * these reside on the stack in vl.c
+        * so they're unusable if we're not in
+        * slirp_select_fill or slirp_select_poll.
+        */
+        global_readfds = NULL;
+        global_writefds = NULL;
+        global_xfds = NULL;
 }
 
 #define ETH_ALEN 6
@@ -538,13 +548,20 @@ void arp_input(const uint8_t *pkt, int pkt_len)
     struct ethhdr *reh = (struct ethhdr *)arp_reply;
     struct arphdr *rah = (struct arphdr *)(arp_reply + ETH_HLEN);
     int ar_op;
+    struct ex_list *ex_ptr;
 
     ar_op = ntohs(ah->ar_op);
     switch(ar_op) {
     case ARPOP_REQUEST:
-        if (!memcmp(ah->ar_tip, &special_addr, 3) &&
-            (ah->ar_tip[3] == CTL_DNS || ah->ar_tip[3] == CTL_ALIAS)) {
-
+        if (!memcmp(ah->ar_tip, &special_addr, 3)) {
+            if (ah->ar_tip[3] == CTL_DNS || ah->ar_tip[3] == CTL_ALIAS) 
+                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])
+                    goto arp_ok;
+            }
+            return;
+        arp_ok:
             /* XXX: make an ARP request to have the client address */
             memcpy(client_ethaddr, eh->h_source, ETH_ALEN);
 
@@ -612,6 +629,7 @@ void if_encap(const uint8_t *ip_data, int ip_data_len)
 
     memcpy(eh->h_dest, client_ethaddr, ETH_ALEN);
     memcpy(eh->h_source, special_ethaddr, ETH_ALEN - 1);
+    /* XXX: not correct */
     eh->h_source[5] = CTL_ALIAS;
     eh->h_proto = htons(ETH_P_IP);
     memcpy(buf + sizeof(struct ethhdr), ip_data, ip_data_len);
@@ -632,3 +650,10 @@ int slirp_redir(int is_udp, int host_port,
     }
     return 0;
 }
+
+int slirp_add_exec(int do_pty, const char *args, int addr_low_byte, 
+                  int guest_port)
+{
+    return add_exec(&exec_list, do_pty, (char *)args, 
+                    addr_low_byte, htons(guest_port));
+}