/* arping - send ARP REQUEST to a neighbour host.
 *
 * Copyright 2013 Sandeep Sharma <sandeep.jack2756@gmail.com>
 * Copyright 2013 Kyungwan Han <asura321@gmail.com>
 *
 * No Standard.

USE_ARPING(NEWTOY(arping, "<1>1s:I:w#<0c#<0AUDbqf[+AU][+Df]", TOYFLAG_USR|TOYFLAG_SBIN))

config ARPING
  bool "arping"
  default n
  help
    usage: arping [-fqbDUA] [-c CNT] [-w TIMEOUT] [-I IFACE] [-s SRC_IP] DST_IP

    Send ARP requests/replies

    -f         Quit on first ARP reply
    -q         Quiet
    -b         Keep broadcasting, don't go unicast
    -D         Duplicated address detection mode
    -U         Unsolicited ARP mode, update your neighbors
    -A         ARP answer mode, update your neighbors
    -c N       Stop after sending N ARP requests
    -w TIMEOUT Time to wait for ARP reply, seconds
    -I IFACE   Interface to use (default eth0)
    -s SRC_IP  Sender IP address
    DST_IP     Target IP address
*/
#define FOR_arping
#include "toys.h"
#include <netinet/ether.h>
#include <netpacket/packet.h>

GLOBALS(
    long count;
    unsigned long time_out;
    char *iface;
    char *src_ip;

    int sockfd;
    unsigned start;
    unsigned end;
    unsigned sent_at;
    unsigned sent_nr;
    unsigned rcvd_nr;
    unsigned brd_sent;
    unsigned rcvd_req;
    unsigned brd_rcv;
    unsigned unicast_flag;
)

struct sockaddr_ll src_pk, dst_pk; 
struct in_addr src_addr, dest_addr;
extern void *mempcpy(void *dest, const void *src, size_t n);

// Gets information of INTERFACE and updates IFINDEX, MAC and IP.
static void get_interface(char *interface, int *ifindex, uint32_t *oip, 
    uint8_t *mac)
{
  struct ifreq req;
  struct sockaddr_in *ip;
  int fd = xsocket(AF_INET, SOCK_RAW, IPPROTO_RAW);

  req.ifr_addr.sa_family = AF_INET;
  strncpy(req.ifr_name, interface, IFNAMSIZ);
  req.ifr_name[IFNAMSIZ-1] = '\0';

  xioctl(fd, SIOCGIFFLAGS, &req);
  if (!(req.ifr_flags & IFF_UP)) return;

  if (oip) {
    xioctl(fd, SIOCGIFADDR, &req);
    ip = (struct sockaddr_in*) &req.ifr_addr;
    *oip = ntohl(ip->sin_addr.s_addr);
  }
  if (ifindex) {
    xioctl(fd, SIOCGIFINDEX, &req);
    *ifindex = req.ifr_ifindex;
  }
  if (mac) {
    xioctl(fd, SIOCGIFHWADDR, &req);
    memcpy(mac, req.ifr_hwaddr.sa_data, 6);
  }
  xclose(fd);
}

// SIGINT handler, Print Number of Packets send or receive details.
static void done(int sig)
{
  if (!(toys.optflags & FLAG_q)) {
    xprintf("Sent %u probe(s) (%u broadcast(s))\n", TT.sent_nr, TT.brd_sent);
    xprintf("Received %u repl%s (%u request(s), %u broadcast(s))\n", 
        TT.rcvd_nr, TT.rcvd_nr == 1 ? "y":"ies", TT.rcvd_req, TT.brd_rcv);
  }
  if (toys.optflags & FLAG_D) exit(!!TT.rcvd_nr);
  //In -U mode, No reply is expected.
  if (toys.optflags & FLAG_U) exit(EXIT_SUCCESS); 
  exit(!TT.rcvd_nr);
}

// Create and Send Packet 
static void send_packet()
{
  int ret;
  unsigned char sbuf[256] = {0,};
  struct arphdr *arp_h = (struct arphdr *) sbuf;
  unsigned char *ptr = (unsigned char *)(arp_h + 1);

  arp_h->ar_hrd = htons(ARPHRD_ETHER);
  arp_h->ar_pro = htons(ETH_P_IP);
  arp_h->ar_hln = src_pk.sll_halen;
  arp_h->ar_pln = 4;  
  arp_h->ar_op = (toys.optflags & FLAG_A) ? htons(ARPOP_REPLY) 
    : htons(ARPOP_REQUEST);

  ptr = mempcpy(ptr, &src_pk.sll_addr, src_pk.sll_halen);
  ptr = mempcpy(ptr, &src_addr, 4);
  if (toys.optflags & FLAG_A) 
    ptr = mempcpy(ptr, &src_pk.sll_addr, src_pk.sll_halen);
  else ptr = mempcpy(ptr, &dst_pk.sll_addr, src_pk.sll_halen);

  ptr = mempcpy(ptr, &dest_addr, 4);
  ret = sendto(TT.sockfd, sbuf, ptr - sbuf, 0, 
      (struct sockaddr *)&dst_pk, sizeof(dst_pk));
  if (ret == ptr - sbuf) {
    struct timeval tval;

    gettimeofday(&tval, NULL);
    TT.sent_at = (tval.tv_sec * 1000000ULL + (tval.tv_usec));
    TT.sent_nr++;
    if (!TT.unicast_flag) TT.brd_sent++;
  }
}

// Receive Packet and filter with valid checks.
static void recv_from(struct sockaddr_ll *from, int *recv_len)
{
  struct in_addr s_ip, d_ip;
  struct arphdr *arp_hdr = (struct arphdr *)toybuf;
  unsigned char *p = (unsigned char *)(arp_hdr + 1);

  if (arp_hdr->ar_op != htons(ARPOP_REQUEST) && 
      arp_hdr->ar_op != htons(ARPOP_REPLY)) return; 

  if (from->sll_pkttype != PACKET_HOST && from->sll_pkttype != PACKET_BROADCAST
      && from->sll_pkttype != PACKET_MULTICAST) return; 

  if (arp_hdr->ar_pro != htons(ETH_P_IP) || (arp_hdr->ar_pln != 4) 
      || (arp_hdr->ar_hln != src_pk.sll_halen) 
      || (*recv_len < (int)(sizeof(*arp_hdr) + 2 * (4 + arp_hdr->ar_hln))))
    return; 

  memcpy(&s_ip.s_addr, p + arp_hdr->ar_hln, 4);
  memcpy(&d_ip.s_addr, p + arp_hdr->ar_hln + 4 + arp_hdr->ar_hln, 4); 

  if (dest_addr.s_addr != s_ip.s_addr) return;
  if (toys.optflags & FLAG_D) {
    if (src_addr.s_addr && src_addr.s_addr != d_ip.s_addr) return;
    if (!memcmp(p, &src_pk.sll_addr, src_pk.sll_halen)) return;
  } else if (src_addr.s_addr != d_ip.s_addr ) return;

  if (!(toys.optflags & FLAG_q)) {
    printf("%scast re%s from %s [%s]",
        from->sll_pkttype == PACKET_HOST ? "Uni" : "Broad",
        arp_hdr->ar_op == htons(ARPOP_REPLY) ? "ply" : "quest",
        inet_ntoa(s_ip), ether_ntoa((struct ether_addr *) p));
    if (TT.sent_at) {  
      unsigned delta;
      struct timeval tval;

      gettimeofday(&tval, NULL);
      delta = (tval.tv_sec * 1000000ULL + (tval.tv_usec)) - TT.sent_at;
      xprintf(" %u.%03ums\n", delta / 1000, delta % 1000);
      xflush();
    }
  }
  TT.rcvd_nr++;
  if (from->sll_pkttype != PACKET_HOST) TT.brd_rcv++;
  if (arp_hdr->ar_op == htons(ARPOP_REQUEST)) TT.rcvd_req++;
  if (toys.optflags & FLAG_f) done(0);
  if (!(toys.optflags & FLAG_b)) {
    memcpy(dst_pk.sll_addr, p, src_pk.sll_halen);
    TT.unicast_flag = 1;
  }
}

// Alarm signal Handle, send packets in one second interval.
static void send_signal(int sig)
{
  struct timeval start;

  gettimeofday(&start, NULL);
  if (!TT.start) 
    TT.end = TT.start = start.tv_sec * 1000 + start.tv_usec / 1000;
  else TT.end = start.tv_sec*1000 + start.tv_usec / 1000;
  if (toys.optflags & FLAG_c) {
    if (!TT.count) done(0);
    TT.count--; 
  }
  if ((toys.optflags & FLAG_w) && ((TT.end - TT.start) > 
        ((TT.time_out)*1000))) done(0);
  send_packet();
  alarm(1);
}

void arping_main(void)
{
  struct ifreq ifr;
  struct sockaddr_ll from;
  socklen_t len;
  int if_index, recv_len;

  if (!(toys.optflags & FLAG_I)) TT.iface = "eth0";
  TT.sockfd = xsocket(AF_PACKET, SOCK_DGRAM, 0);

  memset(&ifr, 0, sizeof(ifr));
  strncpy(ifr.ifr_name, TT.iface, IFNAMSIZ);
  get_interface(TT.iface, &if_index, NULL, NULL);
  src_pk.sll_ifindex = if_index;

  xioctl(TT.sockfd, SIOCGIFFLAGS, (char*)&ifr);
  if (!(ifr.ifr_flags & IFF_UP) && !(toys.optflags & FLAG_q))
    error_exit("Interface \"%s\" is down", TT.iface);
  if ((ifr.ifr_flags & (IFF_NOARP | IFF_LOOPBACK))
      && !(toys.optflags & FLAG_q)) {
    xprintf("Interface \"%s\" is not ARPable\n", TT.iface);
    toys.exitval = (toys.optflags & FLAG_D) ? 0 : 2;
    return;
  }
  if (!inet_aton(*toys.optargs, &dest_addr)) {
    struct hostent *hp = gethostbyname2(*toys.optargs, AF_INET);

    if (!hp) perror_exit("bad address '%s'", *toys.optargs);
    memcpy(&dest_addr, hp->h_addr, 4);
  }
  if ((toys.optflags & FLAG_s) && !(inet_aton(TT.src_ip, &src_addr))) 
    perror_exit("invalid source address '%s'",TT.src_ip);
  if (!(toys.optflags & FLAG_D) && (toys.optflags & FLAG_U) 
      && !src_addr.s_addr) src_addr = dest_addr;
  if (!(toys.optflags & FLAG_D) || src_addr.s_addr) {
    struct sockaddr_in saddr;
    int p_fd = xsocket(AF_INET, SOCK_DGRAM, 0);

    if (setsockopt(p_fd, SOL_SOCKET, SO_BINDTODEVICE, TT.iface,
          strlen(TT.iface))) perror_exit("setsockopt");

    memset(&saddr, 0, sizeof(saddr));
    saddr.sin_family = AF_INET;
    if (src_addr.s_addr) {
      saddr.sin_addr = src_addr;
      if (bind(p_fd, (struct sockaddr*)&saddr, sizeof(saddr))) 
        perror_exit("bind");
    } else {
      uint32_t oip;

      saddr.sin_port = htons(1025);
      saddr.sin_addr = dest_addr;
      if (connect(p_fd, (struct sockaddr *) &saddr, sizeof(saddr)))
        perror_exit("cannot connect to remote host");
      get_interface(TT.iface, NULL, &oip, NULL);
      src_addr.s_addr = htonl(oip);
    }
    xclose(p_fd);
  }

  src_pk.sll_family = AF_PACKET;
  src_pk.sll_protocol = htons(ETH_P_ARP);
  if (bind(TT.sockfd, (struct sockaddr *)&src_pk, sizeof(src_pk))) 
    perror_exit("bind");

  socklen_t alen = sizeof(src_pk);
  getsockname(TT.sockfd, (struct sockaddr *)&src_pk, &alen);
  if (!src_pk.sll_halen) {
    perror_msg("src is not arpable");
    toys.exitval = (toys.optflags & FLAG_D) ? 0 : 2;
    return;
  }
  if (!(toys.optflags & FLAG_q)) {
    xprintf("ARPING to %s", inet_ntoa(dest_addr));
    xprintf(" from %s via %s\n", inet_ntoa(src_addr), TT.iface);
  }

  dst_pk = src_pk;
  //First packet always broadcasts.
  memset(dst_pk.sll_addr, -1, dst_pk.sll_halen);
  signal(SIGINT, done);
  signal(SIGALRM, send_signal);

  send_signal(0); // Send first Broadcast message.
  while (1) {
    len = sizeof(from);
    recv_len = recvfrom(TT.sockfd, toybuf, 4096, 0,
        (struct sockaddr *)&from, &len);
    if (recv_len < 0) continue;
    recv_from(&from, &recv_len);
  }
}
