/*
 * libslirp glue
 *
 * Copyright (c) 2004-2008 Fabrice Bellard
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */
#include "slirp.h"

#include "android/android.h"
#include "android/utils/bufprint.h"
#include "android/utils/debug.h"  /* for dprint */
#include "android/utils/dns.h"
#include "android/utils/ipaddr.h"
#include "android/utils/sockets.h"

#include "android/proxy/proxy_common.h"

#include "hw/hw.h"
#include "qemu-common.h"
#include "qemu/queue.h"
#include "sysemu/char.h"

/* proto types */
static void slirp_net_forward_init(void);

#define  D(...)   VERBOSE_PRINT(slirp,__VA_ARGS__)
#define  DN(...)  do { if (VERBOSE_CHECK(slirp)) dprintn(__VA_ARGS__); } while (0)

/* host address */
uint32_t our_addr_ip;
/* host dns address */
uint32_t dns_addr[DNS_ADDR_MAX];
int      dns_addr_count;

/* Sanity check */
#if DNS_ADDR_MAX != ANDROID_MAX_DNS_SERVERS
#error Invalid DNS_ADDR_MAX definition !! Please update slirp-android/main.h
#endif

/* host loopback address */
uint32_t loopback_addr_ip;

/* address for slirp virtual addresses */
uint32_t  special_addr_ip;

/* virtual address alias for host */
uint32_t alias_addr_ip;

static const uint8_t special_ethaddr[6] = {
    0x52, 0x54, 0x00, 0x12, 0x35, 0x00
};

/* ARP cache for the guest IP addresses (XXX: allow many entries) */
uint8_t client_ethaddr[6];
static ipaddr_t  client_ip;

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;
struct timeval tt;
FILE *lfd;
struct ex_list *exec_list;

/* XXX: suppress those select globals */
fd_set *global_readfds, *global_writefds, *global_xfds;

char slirp_hostname[33];


int slirp_init_dns_servers(const char* servers)
{
    dns_addr_count = android_dns_get_servers(servers, dns_addr);
    if (dns_addr_count < 0) {
        dns_addr[0]    = loopback_addr_ip;
        dns_addr_count = 1;
    }
    return dns_addr_count;
}

int slirp_get_system_dns_servers(void)
{
    int num_servers = android_dns_get_system_servers(dns_addr, DNS_ADDR_MAX);
    if (num_servers >= 0)
        dns_addr_count = num_servers;
    return num_servers;
}

int slirp_parse_dns_servers(const char* servers) {
    int num_servers = android_dns_parse_servers(servers, dns_addr, DNS_ADDR_MAX);
    if (num_servers >= 0)
        dns_addr_count = num_servers;
    return num_servers;
}

int slirp_get_max_dns_servers(void) {
    return DNS_ADDR_MAX;
}

static void slirp_state_save(QEMUFile *f, void *opaque);
static int slirp_state_load(QEMUFile *f, void *opaque, int version_id);

void slirp_init(int restricted, const char *special_ip)
{
#if DEBUG
    int   slirp_logmask = 0;
    char  slirp_logfile[512];
    {
        const char*  env = getenv( "ANDROID_SLIRP_LOGMASK" );
        if (env != NULL)
            slirp_logmask = atoi(env);
         else if (VERBOSE_CHECK(slirp))
            slirp_logmask = DEBUG_DEFAULT;
    }

    {
        char*  p   = slirp_logfile;
        char*  end = p + sizeof(slirp_logfile);

        p = bufprint_temp_file( p, end, "slirp.log" );
        if (p >= end) {
            dprint( "cannot create slirp log file in temporary directory" );
            slirp_logmask = 0;
        }
    }
    if (slirp_logmask) {
        dprint( "sending slirp logs with mask %x to %s", slirp_logmask, slirp_logfile );
        debug_init( slirp_logfile, slirp_logmask );
    }
#endif

    link_up = 1;
    slirp_restrict = restricted;

    if_init();
    ip_init();

    /* Initialise mbufs *after* setting the MTU */
    m_init();

    /* set default addresses */
    inet_strtoip("127.0.0.1", &loopback_addr_ip);

    if (dns_addr_count == 0) {
        slirp_init_dns_servers(NULL);
    }

    inet_strtoip(CTL_SPECIAL, &special_addr_ip);

    alias_addr_ip = special_addr_ip | CTL_ALIAS;
    getouraddr();
    register_savevm(NULL, "slirp", 0, 1, slirp_state_save, slirp_state_load, NULL);

    slirp_net_forward_init();
}

#define CONN_CANFSEND(so) (((so)->so_state & (SS_FCANTSENDMORE|SS_ISFCONNECTED)) == SS_ISFCONNECTED)
#define CONN_CANFRCV(so) (((so)->so_state & (SS_FCANTRCVMORE|SS_ISFCONNECTED)) == SS_ISFCONNECTED)
#define UPD_NFDS(x) if (nfds < (x)) nfds = (x)

/*
 * curtime kept to an accuracy of 1ms
 */
#ifdef _WIN32
static void updtime(void)
{
    struct _timeb tb;

    _ftime(&tb);
    curtime = (u_int)tb.time * (u_int)1000;
    curtime += (u_int)tb.millitm;
}
#else
static void updtime(void)
{
        gettimeofday(&tt, NULL);

	curtime = (u_int)tt.tv_sec * (u_int)1000;
	curtime += (u_int)tt.tv_usec / (u_int)1000;

	if ((tt.tv_usec % 1000) >= 500)
	   curtime++;
}
#endif

void slirp_select_fill(int *pnfds,
                       fd_set *readfds, fd_set *writefds, fd_set *xfds)
{
    struct socket *so, *so_next;
    struct timeval timeout;
    int nfds;
    int tmp_time;

    /* fail safe */
    global_readfds = NULL;
    global_writefds = NULL;
    global_xfds = NULL;

    nfds = *pnfds;
	/*
	 * First, TCP sockets
	 */
	do_slowtimo = 0;
	if (link_up) {
		/*
		 * *_slowtimo needs calling if there are IP fragments
		 * in the fragment queue, or there are TCP connections active
		 */
		do_slowtimo = ((tcb.so_next != &tcb) ||
                (&ipq.ip_link != ipq.ip_link.next));

		for (so = tcb.so_next; so != &tcb; so = so_next) {
			so_next = so->so_next;

			/*
			 * See if we need a tcp_fasttimo
			 */
			if (time_fasttimo == 0 && so->so_tcpcb->t_flags & TF_DELACK)
			   time_fasttimo = curtime; /* Flag when we want a fasttimo */

			/*
			 * NOFDREF can include still connecting to local-host,
			 * newly socreated() sockets etc. Don't want to select these.
	 		 */
			if (so->so_state & SS_NOFDREF || so->s == -1)
			   continue;

            /*
             * don't register proxified socked connections here
             */
            if ((so->so_state & SS_PROXIFIED) != 0)
	            continue;

			/*
			 * Set for reading sockets which are accepting
			 */
			if (so->so_state & SS_FACCEPTCONN) {
                                FD_SET(so->s, readfds);
				UPD_NFDS(so->s);
				continue;
			}

			/*
			 * Set for writing sockets which are connecting
			 */
			if (so->so_state & SS_ISFCONNECTING) {
				FD_SET(so->s, writefds);
				UPD_NFDS(so->s);
				continue;
			}

			/*
			 * Set for writing if we are connected, can send more, and
			 * we have something to send
			 */
			if (CONN_CANFSEND(so) && so->so_rcv.sb_cc) {
				FD_SET(so->s, writefds);
				UPD_NFDS(so->s);
			}

			/*
			 * Set for reading (and urgent data) if we are connected, can
			 * receive more, and we have room for it XXX /2 ?
			 */
			if (CONN_CANFRCV(so) && (so->so_snd.sb_cc < (so->so_snd.sb_datalen/2))) {
				FD_SET(so->s, readfds);
				FD_SET(so->s, xfds);
				UPD_NFDS(so->s);
			}
		}

		/*
		 * UDP sockets
		 */
		for (so = udb.so_next; so != &udb; so = so_next) {
			so_next = so->so_next;

            if ((so->so_state & SS_PROXIFIED) != 0)
                continue;

			/*
			 * See if it's timed out
			 */
			if (so->so_expire) {
				if (so->so_expire <= curtime) {
					udp_detach(so);
					continue;
				} else
					do_slowtimo = 1; /* Let socket expire */
			}

			/*
			 * When UDP packets are received from over the
			 * link, they're sendto()'d straight away, so
			 * no need for setting for writing
			 * Limit the number of packets queued by this session
			 * to 4.  Note that even though we try and limit this
			 * to 4 packets, the session could have more queued
			 * if the packets needed to be fragmented
			 * (XXX <= 4 ?)
			 */
			if ((so->so_state & SS_ISFCONNECTED) && so->so_queued <= 4) {
				FD_SET(so->s, readfds);
				UPD_NFDS(so->s);
			}
		}
	}

	/*
	 * Setup timeout to use minimum CPU usage, especially when idle
	 */

	/*
	 * First, see the timeout needed by *timo
	 */
	timeout.tv_sec = 0;
	timeout.tv_usec = -1;
	/*
	 * If a slowtimo is needed, set timeout to 500ms from the last
	 * slow timeout. If a fast timeout is needed, set timeout within
	 * 200ms of when it was requested.
	 */
	if (do_slowtimo) {
		/* XXX + 10000 because some select()'s aren't that accurate */
		timeout.tv_usec = ((500 - (curtime - last_slowtimo)) * 1000) + 10000;
		if (timeout.tv_usec < 0)
		   timeout.tv_usec = 0;
		else if (timeout.tv_usec > 510000)
		   timeout.tv_usec = 510000;

		/* Can only fasttimo if we also slowtimo */
		if (time_fasttimo) {
			tmp_time = (200 - (curtime - time_fasttimo)) * 1000;
			if (tmp_time < 0)
			   tmp_time = 0;

			/* Choose the smallest of the 2 */
			if (tmp_time < timeout.tv_usec)
			   timeout.tv_usec = (u_int)tmp_time;
		}
	}
    *pnfds = nfds;
}

void slirp_select_poll(fd_set *readfds, fd_set *writefds, fd_set *xfds)
{
    struct socket *so, *so_next;
    int ret;

    global_readfds = readfds;
    global_writefds = writefds;
    global_xfds = xfds;

	/* Update time */
	updtime();

	/*
	 * See if anything has timed out
	 */
	if (link_up) {
		if (time_fasttimo && ((curtime - time_fasttimo) >= 2)) {
			tcp_fasttimo();
			time_fasttimo = 0;
		}
		if (do_slowtimo && ((curtime - last_slowtimo) >= 499)) {
			ip_slowtimo();
			tcp_slowtimo();
			last_slowtimo = curtime;
		}
	}

	/*
	 * Check sockets
	 */
	if (link_up) {
		/*
		 * Check TCP sockets
		 */
		for (so = tcb.so_next; so != &tcb; so = so_next) {
			so_next = so->so_next;

			/*
			 * FD_ISSET is meaningless on these sockets
			 * (and they can crash the program)
			 */
			if (so->so_state & SS_NOFDREF || so->s == -1)
			   continue;

            /*
             * proxified sockets are polled later in this
             * function.
             */
            if ((so->so_state & SS_PROXIFIED) != 0)
                continue;

			/*
			 * Check for URG data
			 * This will soread as well, so no need to
			 * test for readfds below if this succeeds
			 */
			if (FD_ISSET(so->s, xfds))
			   sorecvoob(so);
			/*
			 * Check sockets for reading
			 */
			else if (FD_ISSET(so->s, readfds)) {
				/*
				 * Check for incoming connections
				 */
				if (so->so_state & SS_FACCEPTCONN) {
					tcp_connect(so);
					continue;
				} /* else */
				ret = soread(so);

				/* Output it if we read something */
				if (ret > 0)
				   tcp_output(sototcpcb(so));
			}

			/*
			 * Check sockets for writing
			 */
			if (FD_ISSET(so->s, writefds)) {
			  /*
			   * Check for non-blocking, still-connecting sockets
			   */
			  if (so->so_state & SS_ISFCONNECTING) {
			    /* Connected */
			    so->so_state &= ~SS_ISFCONNECTING;

			    ret = socket_send(so->s, (const void *)&ret, 0);
			    if (ret < 0) {
			      /* XXXXX Must fix, zero bytes is a NOP */
			      if (errno == EAGAIN || errno == EWOULDBLOCK ||
				  errno == EINPROGRESS || errno == ENOTCONN)
				continue;

			      /* else failed */
			      so->so_state = SS_NOFDREF;
			    }
			    /* else so->so_state &= ~SS_ISFCONNECTING; */

			    /*
			     * Continue tcp_input
			     */
			    tcp_input((struct mbuf *)NULL, sizeof(struct ip), so);
			    /* continue; */
			  } else
			    ret = sowrite(so);
			  /*
			   * XXXXX If we wrote something (a lot), there
			   * could be a need for a window update.
			   * In the worst case, the remote will send
			   * a window probe to get things going again
			   */
			}

			/*
			 * Probe a still-connecting, non-blocking socket
			 * to check if it's still alive
	 	 	 */
#ifdef PROBE_CONN
			if (so->so_state & SS_ISFCONNECTING) {
			  ret = socket_recv(so->s, (char *)&ret, 0);

			  if (ret < 0) {
			    /* XXX */
			    if (errno == EAGAIN || errno == EWOULDBLOCK ||
				errno == EINPROGRESS || errno == ENOTCONN)
			      continue; /* Still connecting, continue */

			    /* else failed */
			    so->so_state = SS_NOFDREF;

			    /* tcp_input will take care of it */
			  } else {
			    ret = socket_send(so->s, &ret, 0);
			    if (ret < 0) {
			      /* XXX */
			      if (errno == EAGAIN || errno == EWOULDBLOCK ||
				  errno == EINPROGRESS || errno == ENOTCONN)
				continue;
			      /* else failed */
			      so->so_state = SS_NOFDREF;
			    } else
			      so->so_state &= ~SS_ISFCONNECTING;

			  }
			  tcp_input((struct mbuf *)NULL, sizeof(struct ip),so);
			} /* SS_ISFCONNECTING */
#endif
		}

		/*
		 * Now UDP sockets.
		 * Incoming packets are sent straight away, they're not buffered.
		 * Incoming UDP data isn't buffered either.
		 */
		for (so = udb.so_next; so != &udb; so = so_next) {
			so_next = so->so_next;

            if ((so->so_state & SS_PROXIFIED) != 0)
                continue;

			if (so->s != -1 && FD_ISSET(so->s, readfds)) {
                            sorecvfrom(so);
                        }
		}
	}

	/*
	 * See if we can start outputting
	 */
	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
#define ETH_HLEN 14

#define ETH_P_IP	0x0800		/* Internet Protocol packet	*/
#define ETH_P_ARP	0x0806		/* Address Resolution packet	*/

#define	ARPOP_REQUEST	1		/* ARP request			*/
#define	ARPOP_REPLY	2		/* ARP reply			*/

struct ethhdr
{
	unsigned char	h_dest[ETH_ALEN];	/* destination eth addr	*/
	unsigned char	h_source[ETH_ALEN];	/* source ether addr	*/
	unsigned short	h_proto;		/* packet type ID field	*/
};

struct arphdr
{
	unsigned short	ar_hrd;		/* format of hardware address	*/
	unsigned short	ar_pro;		/* format of protocol address	*/
	unsigned char	ar_hln;		/* length of hardware address	*/
	unsigned char	ar_pln;		/* length of protocol address	*/
	unsigned short	ar_op;		/* ARP opcode (command)		*/

	 /*
	  *	 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		*/
	unsigned char		ar_tha[ETH_ALEN];	/* target hardware address	*/
	unsigned char		ar_tip[4];		/* target IP address		*/
};

static void arp_input(const uint8_t *pkt, int pkt_len)
{
    struct ethhdr *eh = (struct ethhdr *)pkt;
    struct arphdr *ah = (struct arphdr *)(pkt + ETH_HLEN);
    uint8_t arp_reply[ETH_HLEN + sizeof(struct arphdr)];
    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) {
        uint32_t    ar_tip_ip;

    case ARPOP_REQUEST:
        ar_tip_ip = ip_read32h(ah->ar_tip);
        if ((ar_tip_ip & 0xffffff00) == special_addr_ip) {
            uint32_t  ar_tip_low = ar_tip_ip & 0xff;
            if ( CTL_IS_DNS(ar_tip_low) || ar_tip_low == CTL_ALIAS)
                goto arp_ok;
            for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next) {
                if ((uint32_t)ex_ptr->ex_addr == ar_tip_low)
                    goto arp_ok;
            }
            return;
        arp_ok:
            /* XXX: make an ARP request to have the client address */
            memcpy(client_ethaddr, eh->h_source, ETH_ALEN);

            /* 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] = ar_tip_low;
            reh->h_proto = htons(ETH_P_ARP);

            rah->ar_hrd = htons(1);
            rah->ar_pro = htons(ETH_P_IP);
            rah->ar_hln = ETH_ALEN;
            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);
            memcpy(rah->ar_tha, ah->ar_sha, ETH_ALEN);
            memcpy(rah->ar_tip, ah->ar_sip, 4);
            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) &&
            ip_equal( ip_read(ah->ar_sip), client_ip )) {
            memcpy(client_ethaddr, ah->ar_sha, ETH_ALEN);
        }
        break;
    default:
        break;
    }
}

void slirp_input(const uint8_t *pkt, int pkt_len)
{
    struct mbuf *m;
    int proto;

    if (pkt_len < ETH_HLEN)
        return;

    proto = ntohs(*(uint16_t *)(pkt + 12));
    switch(proto) {
    case ETH_P_ARP:
        arp_input(pkt, pkt_len);
        break;
    case ETH_P_IP:
        m = m_get();
        if (!m)
            return;
        /* Note: we add to align the IP header */
        if (M_FREEROOM(m) < pkt_len + 2) {
            m_inc(m, pkt_len + 2);
        }
        m->m_len = pkt_len + 2;
        memcpy(m->m_data + 2, pkt, pkt_len);

        m->m_data += 2 + ETH_HLEN;
        m->m_len -= 2 + ETH_HLEN;

        ip_input(m);
        break;
    default:
        break;
    }
}

/* output the IP packet to the ethernet device */
void if_encap(const uint8_t *ip_data, int ip_data_len)
{
    uint8_t buf[1600];
    struct ethhdr *eh = (struct ethhdr *)buf;

    if (ip_data_len + ETH_HLEN > (int)sizeof(buf))
        return;

    if (!memcmp(client_ethaddr, zero_ethaddr, ETH_ALEN)) {
        uint8_t arp_req[ETH_HLEN + sizeof(struct arphdr)];
        struct ethhdr *reh = (struct ethhdr *)arp_req;
        struct arphdr *rah = (struct arphdr *)(arp_req + ETH_HLEN);
        const struct ip *iph = (const struct ip *)ip_data;

        /* If the client addr is not known, there is no point in
           sending the packet to it. Normally the sender should have
           done an ARP request to get its MAC address. Here we do it
           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;
        reh->h_proto = htons(ETH_P_ARP);
        rah->ar_hrd = htons(1);
        rah->ar_pro = htons(ETH_P_IP);
        rah->ar_hln = ETH_ALEN;
        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;
        /* source IP */
        ip_write32h(alias_addr_ip, rah->ar_sip);
        /* target hw addr (none) */
        memset(rah->ar_tha, 0, ETH_ALEN);
        /* target IP */
        ip_write( iph->ip_dst, rah->ar_tip );
        client_ip   = 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);
        /* 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);
        slirp_output(buf, ip_data_len + ETH_HLEN);
    }
}


/*---------------------------------------------------*/
/* User mode network stack restrictions */
struct fw_allow_entry {
    struct fw_allow_entry* next;
    unsigned long dst_addr;   /* host byte order */
    /* Allowed port range. dst_lport should be the same as dst_hport for a
     * single port. */
    unsigned short dst_lport; /* host byte order */
    unsigned short dst_hport; /* host byte order */
};

static int drop_udp = 0;
static int drop_tcp = 0;
static struct fw_allow_entry* allow_tcp_entries = NULL;
static struct fw_allow_entry* allow_udp_entries = NULL;
static FILE* drop_log_fd = NULL;
static FILE* dns_log_fd = NULL;
static int max_dns_conns = -1;   /* unlimited max DNS connections by default */
static int slirp_net_forward_inited = 0;

void slirp_drop_udp() {
    drop_udp = 1;
}

void slirp_drop_tcp() {
    drop_tcp = 1;
}

/* TCP traffic forwarding to a sink - If enabled, all TCP traffic to any
 * ip/port that is not explicitly forwared using '-net-forward', and which would
 * otherwise be dropped if '-drop-tcp' has been specified, is redirected to the
 * specified ip:port
 */
int forward_dropped_tcp2sink = 0;
static unsigned long tcp_sink_ip;
int tcp_sink_port;

void slirp_forward_dropped_tcp2sink(unsigned long sink_ip, int sink_port) {
    tcp_sink_ip = sink_ip;
    tcp_sink_port = sink_port;
    forward_dropped_tcp2sink = 1;
}

int slirp_should_forward_dropped_tcp2sink() {
    return forward_dropped_tcp2sink;
}

unsigned long slirp_get_tcp_sink_ip() {
    return tcp_sink_ip;
}
int slirp_get_tcp_sink_port() {
    return tcp_sink_port;
}

/* Fill in the firewall rules. dst_lport and dst_hport are in host byte order */
void slirp_add_allow(unsigned long dst_addr,
                     int dst_lport, int dst_hport,
                     u_int8_t proto) {

    struct fw_allow_entry** ate;
    switch (proto) {
      case IPPROTO_TCP:
          ate = &allow_tcp_entries;
          break;
      case IPPROTO_UDP:
          ate = &allow_udp_entries;
          break;
      default:
          return; // unknown protocol for the FW
    }

    while(*ate != NULL)
        ate = &(*ate)->next;

    *ate = malloc(sizeof(**ate));
    if (*ate == NULL) {
        DEBUG_MISC((dfd,
                    "Unable to create new firewall record, malloc failed\n"));
        exit(-1);
    }

    (*ate)->next = NULL;
    (*ate)->dst_addr = dst_addr;
    (*ate)->dst_lport = dst_lport;
    (*ate)->dst_hport = dst_hport;
}

void slirp_drop_log_fd(FILE* fd) {
    drop_log_fd = fd;
}

void slirp_dns_log_fd(FILE* fd) {
    dns_log_fd = fd;
}

FILE* get_slirp_drop_log_fd(void) {
  return drop_log_fd;
}

FILE* get_slirp_dns_log_fd(void) {
  return dns_log_fd;
}

/* Address and ports are in host byte order */
int slirp_should_drop(unsigned long dst_addr,
                      int dst_port,
                      u_int8_t proto) {

    struct fw_allow_entry* ate;

    switch (proto) {
        case IPPROTO_TCP:
            if (drop_tcp != 0)
                ate = allow_tcp_entries;
            else
                return 0;
            break;
        case IPPROTO_UDP:
            if (drop_udp != 0)
                ate = allow_udp_entries;
            else
                return 0;
            break;
        default:
            return 1;  // unknown protocol for the FW
    }

    while(ate) {
        if ((ate->dst_lport <= dst_port) && (dst_port <= ate->dst_hport)) {
            // allow any destination if 0
            if (ate->dst_addr == 0 || ate->dst_addr == dst_addr)
                return 0;
        }
        ate = ate->next;
    }

    return 1;
}

/*
 * log DNS requests in a separate log
 */
int
slirp_log_dns(struct mbuf* m, int dropped) {
    char dns_query[256];  // max allowable dns name size
    int c = 0;
    int i= 0;
    int index = 0;
    int offset = 40 + 1;  // udp/ip headers length + 1;
    int trim_bytes = 4;

    if (!dns_log_fd)
        return -1;

    /* We assume one DNS name per query: 300 = 255 (max dns name length)
     * + 40 (udp/ip hdr) + 1 byte DNS peamble + 4 bytes DNS suffix
     */
    if (m->m_len < offset || m->m_len > 300) {
        DEBUG_MISC((dfd,"Malformed DNS qeury, length %d \n", (int)m->m_len));
        return -1;
    }
    for (i = offset; i < m->m_len - trim_bytes && index < (int)sizeof(dns_query); i++, index++) {
        c = m->m_data[i];
        if (c < ' ' || c > '~')
            c = '.';

        dns_query[index] = (char)c;
    }
    dns_query[index] = '\0';
    if (!dropped) {
        fprintf(dns_log_fd, "Sent DNS query for, %s\n" , dns_query);
    } else {
        fprintf(dns_log_fd, "Dropped DNS query for, %s\n" , dns_query);
    }
    fflush(dns_log_fd);
    return 1;
}

/*
 * log DNS requests in a separate log
 */
int
slirp_dump_dns(struct mbuf* m) {

    if (!dns_log_fd)
        return 0;
    // first we write the length of the record then the record (IP packet)
    if (!fwrite(&(m->m_len), sizeof(int), 1, dns_log_fd) ||
        !fwrite(m->m_data, m->m_len, 1, dns_log_fd)) {
        return 0;
    }

    fflush(dns_log_fd);
    return 1;
}

/* Log dropped/accepted packet info */
int slirp_drop_log(const char* format, ...) {
    va_list args;

    if (!drop_log_fd)
        return 0;

    va_start(args, format);
    vfprintf(drop_log_fd, format, args);
    va_end(args);

    fflush(drop_log_fd);

    return 1;
}


/* Set max DNS requests allowed to be issued from the VM */
void slirp_set_max_dns_conns(int num_conns) {
    max_dns_conns = num_conns;
}

int slirp_get_max_dns_conns() {
    return max_dns_conns;
}

/* generic guest network redirection functionality for ipv4 */
struct net_forward_entry {
    QTAILQ_ENTRY(net_forward_entry) next;
    /* ip addresses are also in host byte order */
    unsigned long dest_ip;            /* the destination address they try to contact */
    unsigned long dest_mask;          /* the mask to apply to the address for matching */
    /* Range of ports they were trying to contact. In case of a single port,
     * dest_lport should be the same as dest_hport */
    int dest_lport; /* Host byte order */
    int dest_hport; /* Host byte order */

    unsigned long  redirect_ip;
    int redirect_port; /* Host byte order */
};

static QTAILQ_HEAD(net_forwardq, net_forward_entry) net_forwards;

static void slirp_net_forward_init(void)
{
    if (!slirp_net_forward_inited) {
      QTAILQ_INIT(&net_forwards);
      slirp_net_forward_inited = 1;
    }
}

/* all addresses and ports ae in host byte order */
void slirp_add_net_forward(unsigned long dest_ip, unsigned long dest_mask,
                           int dest_lport, int dest_hport,
                           unsigned long redirect_ip, int redirect_port)
{
    slirp_net_forward_init();

    struct net_forward_entry *entry = malloc(sizeof(*entry));
    if (entry == NULL) {
        DEBUG_MISC((dfd, "Unable to create new forwarding entry, malloc failed\n"));
        exit(-1);
    }

    entry->dest_ip = dest_ip;
    entry->dest_mask = dest_mask;
    entry->dest_lport = dest_lport;
    entry->dest_hport = dest_hport;
    entry->redirect_ip = redirect_ip;
    entry->redirect_port = redirect_port;

    QTAILQ_INSERT_TAIL(&net_forwards, entry, next);
}

/* remote_port and redir_port arguments
 * are in network byte order (tcp_subr.c) */
int slirp_should_net_forward(unsigned long remote_ip, int remote_port,
                             unsigned long *redirect_ip, int *redirect_port)
{
    struct net_forward_entry *entry;

    for (entry = net_forwards.tqh_first;
         entry != NULL; entry = entry->next.tqe_next) {

        if ((entry->dest_lport <= remote_port)
            && (remote_port <= entry->dest_hport)) {
            if ((entry->dest_ip & entry->dest_mask)
                == (remote_ip & entry->dest_mask)) {
              *redirect_ip = entry->redirect_ip;
              *redirect_port = entry->redirect_port;
              return 1;
            }
        }
    }

    return 0;
}

/*---------------------------------------------------*/




static void _slirp_redir_loop(void (*func)(void *opaque, int is_udp,
                                           const SockAddress *laddr,
                                           const SockAddress *faddr),
                              void *opaque, int is_udp)
{
    struct socket *head = (is_udp ? &udb : &tcb);
    struct socket *so;

    for (so = head->so_next; so != head; so = so->so_next) {
        SockAddress  local, foreign;

		sock_address_init_inet(&local, so->so_laddr_ip, so->so_laddr_port);
		sock_address_init_inet(&foreign, so->so_faddr_ip, so->so_faddr_port);
        func(opaque, is_udp,
             &local, &foreign);
    }
}

void slirp_redir_loop(void (*func)(void *opaque, int is_udp,
                                   const SockAddress *laddr,
                                   const SockAddress *faddr),
                     void *opaque)
{
    _slirp_redir_loop(func, opaque, 0);
    _slirp_redir_loop(func, opaque, 1);
}

/* Unlistens a redirection
 *
 * Return value: number of redirs removed */
int slirp_redir_rm(int is_udp, int host_port)
{
    struct socket *so;
    struct socket *head = (is_udp ? &udb : &tcb);
    int n = 0;

 loop_again:
    for (so = head->so_next; so != head; so = so->so_next) {
        if (so->so_faddr_port == host_port) {
            close(so->s);
            sofree(so);
            n++;
            goto loop_again;
        }
    }

    return n;
}

int slirp_redir(int is_udp, int host_port,
                uint32_t  guest_ip, int guest_port)
{
    if (is_udp) {
        if (!udp_listen(host_port,
                        guest_ip,
                        guest_port, 0))
            return -1;
    } else {
        struct socket* s4 = solisten(host_port, guest_ip, guest_port, 0);
        struct socket* s6 = solisten(host_port, guest_ip, guest_port, SS_IPV6);
        if (!s4 && !s6)
            return -1;
    }
    return 0;
}

int  slirp_unredir(int  is_udp, int  host_port)
{
    if (is_udp)
        return udp_unlisten( host_port );
    else {
        if (sounlisten( host_port ))
            return -1;
        // It's possible we are listening on both ipv4/ipv6 ports.
        // Just try unlisten again.
        sounlisten( host_port );
        return 0;
    }
}

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, htons(guest_port));
}

ssize_t slirp_send(struct socket *so, const void *buf, size_t len, int flags)
{
	if (so->s == -1 && so->extra) {
		qemu_chr_write(so->extra, buf, len);
		return len;
	}

	return send(so->s, buf, len, flags);
}

static struct socket *slirp_find_ctl_socket(int addr_low_byte, int guest_port)
{
	struct socket *so;

	for (so = tcb.so_next; so != &tcb; so = so->so_next) {
		if ((so->so_faddr_ip & 0xffffff00) ==
				special_addr_ip
				&& ((so->so_faddr_port & 0xff) ==
				addr_low_byte)
				&& so->so_faddr_port == guest_port)
			return so;
	}

	return NULL;
}

size_t slirp_socket_can_recv(int addr_low_byte, int guest_port)
{
	struct iovec iov[2];
	struct socket *so;

    if (!link_up)
        return 0;

	so = slirp_find_ctl_socket(addr_low_byte, guest_port);

	if (!so || so->so_state & SS_NOFDREF)
		return 0;

	if (!CONN_CANFRCV(so) || so->so_snd.sb_cc >= (so->so_snd.sb_datalen/2))
		return 0;

	return sopreprbuf(so, iov, NULL);
}

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);

    if (!so)
        return;

    ret = soreadbuf(so, (const char *)buf, size);

    if (ret > 0)
        tcp_output(sototcpcb(so));
}

static void slirp_tcp_save(QEMUFile *f, struct tcpcb *tp)
{
    int i;

    qemu_put_sbe16(f, tp->t_state);
    for (i = 0; i < TCPT_NTIMERS; i++)
        qemu_put_sbe16(f, tp->t_timer[i]);
    qemu_put_sbe16(f, tp->t_rxtshift);
    qemu_put_sbe16(f, tp->t_rxtcur);
    qemu_put_sbe16(f, tp->t_dupacks);
    qemu_put_be16(f, tp->t_maxseg);
    qemu_put_sbyte(f, tp->t_force);
    qemu_put_be16(f, tp->t_flags);
    qemu_put_be32(f, tp->snd_una);
    qemu_put_be32(f, tp->snd_nxt);
    qemu_put_be32(f, tp->snd_up);
    qemu_put_be32(f, tp->snd_wl1);
    qemu_put_be32(f, tp->snd_wl2);
    qemu_put_be32(f, tp->iss);
    qemu_put_be32(f, tp->snd_wnd);
    qemu_put_be32(f, tp->rcv_wnd);
    qemu_put_be32(f, tp->rcv_nxt);
    qemu_put_be32(f, tp->rcv_up);
    qemu_put_be32(f, tp->irs);
    qemu_put_be32(f, tp->rcv_adv);
    qemu_put_be32(f, tp->snd_max);
    qemu_put_be32(f, tp->snd_cwnd);
    qemu_put_be32(f, tp->snd_ssthresh);
    qemu_put_sbe16(f, tp->t_idle);
    qemu_put_sbe16(f, tp->t_rtt);
    qemu_put_be32(f, tp->t_rtseq);
    qemu_put_sbe16(f, tp->t_srtt);
    qemu_put_sbe16(f, tp->t_rttvar);
    qemu_put_be16(f, tp->t_rttmin);
    qemu_put_be32(f, tp->max_sndwnd);
    qemu_put_byte(f, tp->t_oobflags);
    qemu_put_byte(f, tp->t_iobc);
    qemu_put_sbe16(f, tp->t_softerror);
    qemu_put_byte(f, tp->snd_scale);
    qemu_put_byte(f, tp->rcv_scale);
    qemu_put_byte(f, tp->request_r_scale);
    qemu_put_byte(f, tp->requested_s_scale);
    qemu_put_be32(f, tp->ts_recent);
    qemu_put_be32(f, tp->ts_recent_age);
    qemu_put_be32(f, tp->last_ack_sent);
}

static void slirp_sbuf_save(QEMUFile *f, struct sbuf *sbuf)
{
    uint32_t off;

    qemu_put_be32(f, sbuf->sb_cc);
    qemu_put_be32(f, sbuf->sb_datalen);
    off = (uint32_t)(sbuf->sb_wptr - sbuf->sb_data);
    qemu_put_sbe32(f, off);
    off = (uint32_t)(sbuf->sb_rptr - sbuf->sb_data);
    qemu_put_sbe32(f, off);
    qemu_put_buffer(f, (unsigned char*)sbuf->sb_data, sbuf->sb_datalen);
}

static void slirp_socket_save(QEMUFile *f, struct socket *so)
{
    qemu_put_be32(f, so->so_urgc);
    qemu_put_be32(f, so->so_faddr_ip);
    qemu_put_be32(f, so->so_laddr_ip);
    qemu_put_be16(f, so->so_faddr_port);
    qemu_put_be16(f, so->so_laddr_port);
    qemu_put_byte(f, so->so_iptos);
    qemu_put_byte(f, so->so_emu);
    qemu_put_byte(f, so->so_type);
    qemu_put_be32(f, so->so_state);
    slirp_sbuf_save(f, &so->so_rcv);
    slirp_sbuf_save(f, &so->so_snd);
    slirp_tcp_save(f, so->so_tcpcb);
}

static void slirp_state_save(QEMUFile *f, void *opaque)
{
    struct ex_list *ex_ptr;

    for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next)
        if (ex_ptr->ex_pty == 3) {
            struct socket *so;
            so = slirp_find_ctl_socket(ex_ptr->ex_addr, ntohs(ex_ptr->ex_fport));
            if (!so)
                continue;

            qemu_put_byte(f, 42);
            slirp_socket_save(f, so);
        }
    qemu_put_byte(f, 0);
}

static void slirp_tcp_load(QEMUFile *f, struct tcpcb *tp)
{
    int i;

    tp->t_state = qemu_get_sbe16(f);
    for (i = 0; i < TCPT_NTIMERS; i++)
        tp->t_timer[i] = qemu_get_sbe16(f);
    tp->t_rxtshift = qemu_get_sbe16(f);
    tp->t_rxtcur = qemu_get_sbe16(f);
    tp->t_dupacks = qemu_get_sbe16(f);
    tp->t_maxseg = qemu_get_be16(f);
    tp->t_force = qemu_get_sbyte(f);
    tp->t_flags = qemu_get_be16(f);
    tp->snd_una = qemu_get_be32(f);
    tp->snd_nxt = qemu_get_be32(f);
    tp->snd_up = qemu_get_be32(f);
    tp->snd_wl1 = qemu_get_be32(f);
    tp->snd_wl2 = qemu_get_be32(f);
    tp->iss = qemu_get_be32(f);
    tp->snd_wnd = qemu_get_be32(f);
    tp->rcv_wnd = qemu_get_be32(f);
    tp->rcv_nxt = qemu_get_be32(f);
    tp->rcv_up = qemu_get_be32(f);
    tp->irs = qemu_get_be32(f);
    tp->rcv_adv = qemu_get_be32(f);
    tp->snd_max = qemu_get_be32(f);
    tp->snd_cwnd = qemu_get_be32(f);
    tp->snd_ssthresh = qemu_get_be32(f);
    tp->t_idle = qemu_get_sbe16(f);
    tp->t_rtt = qemu_get_sbe16(f);
    tp->t_rtseq = qemu_get_be32(f);
    tp->t_srtt = qemu_get_sbe16(f);
    tp->t_rttvar = qemu_get_sbe16(f);
    tp->t_rttmin = qemu_get_be16(f);
    tp->max_sndwnd = qemu_get_be32(f);
    tp->t_oobflags = qemu_get_byte(f);
    tp->t_iobc = qemu_get_byte(f);
    tp->t_softerror = qemu_get_sbe16(f);
    tp->snd_scale = qemu_get_byte(f);
    tp->rcv_scale = qemu_get_byte(f);
    tp->request_r_scale = qemu_get_byte(f);
    tp->requested_s_scale = qemu_get_byte(f);
    tp->ts_recent = qemu_get_be32(f);
    tp->ts_recent_age = qemu_get_be32(f);
    tp->last_ack_sent = qemu_get_be32(f);
    tcp_template(tp);
}

static int slirp_sbuf_load(QEMUFile *f, struct sbuf *sbuf)
{
    uint32_t off, sb_cc, sb_datalen;

    sb_cc = qemu_get_be32(f);
    sb_datalen = qemu_get_be32(f);

    sbreserve(sbuf, sb_datalen);

    if (sbuf->sb_datalen != sb_datalen)
        return -ENOMEM;

    sbuf->sb_cc = sb_cc;

    off = qemu_get_sbe32(f);
    sbuf->sb_wptr = sbuf->sb_data + off;
    off = qemu_get_sbe32(f);
    sbuf->sb_rptr = sbuf->sb_data + off;
    qemu_get_buffer(f, (unsigned char*)sbuf->sb_data, sbuf->sb_datalen);

    return 0;
}

static int slirp_socket_load(QEMUFile *f, struct socket *so)
{
    if (tcp_attach(so) < 0)
        return -ENOMEM;

    so->so_urgc = qemu_get_be32(f);
    so->so_faddr_ip = qemu_get_be32(f);
    so->so_laddr_ip = qemu_get_be32(f);
    so->so_faddr_port = qemu_get_be16(f);
    so->so_laddr_port = qemu_get_be16(f);
    so->so_iptos = qemu_get_byte(f);
    so->so_emu = qemu_get_byte(f);
    so->so_type = qemu_get_byte(f);
    so->so_state = qemu_get_be32(f);
    if (slirp_sbuf_load(f, &so->so_rcv) < 0)
        return -ENOMEM;
    if (slirp_sbuf_load(f, &so->so_snd) < 0)
        return -ENOMEM;
    slirp_tcp_load(f, so->so_tcpcb);

    return 0;
}

static int slirp_state_load(QEMUFile *f, void *opaque, int version_id)
{
    struct ex_list *ex_ptr;
    int r;

    while ((r = qemu_get_byte(f))) {
        int ret;
        struct socket *so = socreate();

        if (!so)
            return -ENOMEM;

        ret = slirp_socket_load(f, so);

        if (ret < 0)
            return ret;

        if ((so->so_faddr_ip & 0xffffff00) != special_addr_ip)
            return -EINVAL;

        for (ex_ptr = exec_list; ex_ptr; ex_ptr = ex_ptr->ex_next)
            if (ex_ptr->ex_pty == 3 &&
                    (so->so_faddr_ip & 0xff) == ex_ptr->ex_addr &&
                    so->so_faddr_port == ex_ptr->ex_fport)
                break;

        if (!ex_ptr)
            return -EINVAL;

        so->extra = (void *)ex_ptr->ex_exec;
    }

    return 0;
}
