/*
 dhcp_release6 --iface <interface> --client-id <client-id> --server-id
 server-id --iaid <iaid>  --ip <IP>  [--dry-run] [--help]
 MUST be run as root - will fail otherwise
 */

/* Send a DHCPRELEASE message  to IPv6 multicast address  via the specified interface
 to tell the local DHCP server to delete a particular lease.
 
 The interface argument is the interface in which a DHCP
 request _would_ be received if it was coming from the client,
 rather than being faked up here.
 
 The client-id argument is colon-separated hex string and mandatory. Normally
 it can be found in leases file both on client and server

 The server-id argument is colon-separated hex string and mandatory. Normally
 it can be found in leases file both on client and server.
 
 The iaid argument is numeric string and mandatory. Normally
 it can be found in leases file both on client and server.
 
 IP is an IPv6 address to release
 
 If --dry-run is specified, dhcp_release6 just prints hexadecimal representation of
 packet to send to stdout and exits.
 
 If --help is specified, dhcp_release6 print usage information to stdout and exits
 
 
 
 */
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <strings.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <getopt.h>
#include <errno.h>
#include <unistd.h>

#define NOT_REPLY_CODE 115
typedef unsigned char u8;
typedef unsigned short u16;
typedef unsigned int u32;

enum DHCP6_TYPES
  {
    SOLICIT = 1,
    ADVERTISE = 2,
    REQUEST = 3,
    CONFIRM = 4,
    RENEW = 5,
    REBIND = 6,
    REPLY = 7,
    RELEASE = 8,
    DECLINE = 9,
    RECONFIGURE = 10,
    INFORMATION_REQUEST = 11,
    RELAY_FORW = 12,
    RELAY_REPL = 13
    
  };

enum DHCP6_OPTIONS
  {
    CLIENTID = 1,
    SERVERID = 2,
    IA_NA = 3,
    IA_TA = 4,
    IAADDR = 5,
    ORO = 6,
    PREFERENCE = 7,
    ELAPSED_TIME = 8,
    RELAY_MSG = 9,
    AUTH = 11,
    UNICAST = 12,
    STATUS_CODE = 13,
    RAPID_COMMIT = 14,
    USER_CLASS = 15,
    VENDOR_CLASS = 16,
    VENDOR_OPTS = 17,
    INTERFACE_ID = 18,
    RECONF_MSG = 19,
    RECONF_ACCEPT = 20,
  };

enum DHCP6_STATUSES
  {
    SUCCESS = 0,
    UNSPEC_FAIL = 1,
    NOADDR_AVAIL=2,
    NO_BINDING  = 3,
    NOT_ON_LINK = 4,
    USE_MULTICAST =5
  };

static struct option longopts[] = {
  {"ip", required_argument, 0, 'a' },
  {"server-id", required_argument, 0, 's' },
  {"client-id", required_argument, 0, 'c' },
  {"iface", required_argument, 0, 'n' },
  {"iaid", required_argument, 0, 'i' },
  {"dry-run", no_argument, 0, 'd' },
  {"help", no_argument, 0, 'h' },
  {0,     0,           0,   0 }
};

const short DHCP6_CLIENT_PORT = 546;
const short DHCP6_SERVER_PORT = 547;

const char*  DHCP6_MULTICAST_ADDRESS = "ff02::1:2";

struct dhcp6_option {
  uint16_t type;
  uint16_t len;
  char  value[1024];
};

struct dhcp6_iaaddr_option {
  uint16_t type;
  uint16_t len;
  struct in6_addr ip;
  uint32_t preferred_lifetime;
  uint32_t valid_lifetime;
};

struct dhcp6_iana_option {
  uint16_t type;
  uint16_t len;
  uint32_t iaid;
  uint32_t t1;
  uint32_t t2;
  char options[1024];
};


struct dhcp6_packet {
  size_t len;
  char buf[2048];  
};

size_t pack_duid(const char* str, char* dst)
{
  char* tmp = strdup(str);
  char* tmp_to_free = tmp;
  char *ptr;
  uint8_t write_pos = 0;
  while ((ptr = strtok (tmp, ":")))
    {
      dst[write_pos] = (uint8_t) strtol(ptr, NULL, 16);
      write_pos += 1;
      tmp = NULL;
    }
  
  free(tmp_to_free);
  return write_pos;
}

struct dhcp6_option create_client_id_option(const char* duid)
{
  struct dhcp6_option option;
  option.type = htons(CLIENTID);
  bzero(option.value, sizeof(option.value));
  option.len  = htons(pack_duid(duid, option.value));
  return option;
}

struct dhcp6_option create_server_id_option(const char* duid)
{
  struct dhcp6_option   option;
  option.type = htons(SERVERID);
  bzero(option.value, sizeof(option.value));
  option.len  = htons(pack_duid(duid, option.value));
  return option;
}

struct dhcp6_iaaddr_option create_iaadr_option(const char* ip)
{
  struct dhcp6_iaaddr_option result;
  result.type =htons(IAADDR);
  /* no suboptions needed here, so length is 24  */
  result.len = htons(24);
  result.preferred_lifetime = 0;
  result.valid_lifetime = 0;
  int s = inet_pton(AF_INET6, ip, &(result.ip));
  if (s <= 0) {
    if (s == 0)
      fprintf(stderr, "Not in presentation format");
    else
      perror("inet_pton");
    exit(EXIT_FAILURE);
  }

  return result;
}

struct dhcp6_iana_option  create_iana_option(const char * iaid, struct dhcp6_iaaddr_option  ia_addr)
{
  struct dhcp6_iana_option  result;
  result.type = htons(IA_NA);
  result.iaid = htonl(atoi(iaid));
  result.t1 = 0;
  result.t2 = 0;
  result.len = htons(12 + ntohs(ia_addr.len) + 2 * sizeof(uint16_t));
  memcpy(result.options, &ia_addr, ntohs(ia_addr.len) + 2 * sizeof(uint16_t));
  return result;
}

struct dhcp6_packet create_release_packet(const char* iaid, const char* ip, const char* client_id, const char* server_id)
{
  struct dhcp6_packet result;
  bzero(result.buf, sizeof(result.buf));
  /* message_type */
  result.buf[0] = RELEASE;
  /* tx_id */
  bzero(result.buf+1, 3);
  
  struct dhcp6_option client_option = create_client_id_option(client_id);
  struct dhcp6_option server_option = create_server_id_option(server_id);
  struct dhcp6_iaaddr_option iaaddr_option = create_iaadr_option(ip);
  struct dhcp6_iana_option iana_option = create_iana_option(iaid, iaaddr_option);
  int offset = 4;
  memcpy(result.buf + offset, &client_option, ntohs(client_option.len) + 2*sizeof(uint16_t));
  offset += (ntohs(client_option.len)+ 2 *sizeof(uint16_t) );
  memcpy(result.buf + offset, &server_option, ntohs(server_option.len) + 2*sizeof(uint16_t) );
  offset += (ntohs(server_option.len)+ 2* sizeof(uint16_t));
  memcpy(result.buf + offset, &iana_option, ntohs(iana_option.len) + 2*sizeof(uint16_t) );
  offset += (ntohs(iana_option.len)+ 2* sizeof(uint16_t));
  result.len = offset;
  return result;
}

uint16_t parse_iana_suboption(char* buf, size_t len)
{
  size_t current_pos = 0;
  char option_value[1024];
  while (current_pos < len)
    {
      uint16_t option_type, option_len;
      memcpy(&option_type,buf + current_pos, sizeof(uint16_t));
      memcpy(&option_len,buf + current_pos + sizeof(uint16_t), sizeof(uint16_t));
      option_type = ntohs(option_type);
      option_len = ntohs(option_len);
      current_pos += 2 * sizeof(uint16_t);
      if (option_type == STATUS_CODE)
	{
	  uint16_t status;
	  memcpy(&status, buf + current_pos, sizeof(uint16_t));
	  status = ntohs(status);
	  if (status != SUCCESS)
	    {
	      memcpy(option_value, buf + current_pos + sizeof(uint16_t) , option_len - sizeof(uint16_t));
	      option_value[option_len-sizeof(uint16_t)] ='\0';
	      fprintf(stderr, "Error: %s\n", option_value);
            }
	  return status;
        }
    }

  return -2;
}

int16_t parse_packet(char* buf, size_t len)
{
  int16_t ret = -1;
  uint8_t type = buf[0];
  /*skipping tx id. you need it, uncomment following line
    uint16_t tx_id = ntohs((buf[1] <<16) + (buf[2] <<8) + buf[3]);
  */
  size_t current_pos = 4;
  if (type != REPLY )
    return NOT_REPLY_CODE;
  
  char option_value[1024];
  while (current_pos < len)
    {
      uint16_t option_type, option_len;
      memcpy(&option_type,buf + current_pos, sizeof(uint16_t));
      memcpy(&option_len,buf + current_pos + sizeof(uint16_t), sizeof(uint16_t));
      option_type = ntohs(option_type);
      option_len = ntohs(option_len);
      current_pos += 2 * sizeof(uint16_t);
      if (option_type == STATUS_CODE)
	{
	  uint16_t status;
	  memcpy(&status, buf + current_pos, sizeof(uint16_t));
	  status = ntohs(status);
	  if (status != SUCCESS)
	    {
	      memcpy(option_value, buf + current_pos +sizeof(uint16_t) , option_len -sizeof(uint16_t));
	      fprintf(stderr, "Error: %d %s\n", status, option_value);
	      return status;
	    }

	  /* Got success status, return that if there's no specific error in an IA_NA. */
	  ret = SUCCESS;   
        }

      if (option_type == IA_NA )
	{
	  uint16_t result = parse_iana_suboption(buf + current_pos +24, option_len -24);
	  if (result)
	    return result;
	}
      
      current_pos += option_len;
    }

  return ret;
}

void usage(const char* arg, FILE* stream)
{
  const char* usage_string ="--ip IPv6 --iface IFACE --server-id SERVER_ID --client-id CLIENT_ID --iaid IAID [--dry-run] | --help";
  fprintf (stream, "Usage: %s %s\n", arg, usage_string);   
}

int send_release_packet(const char* iface, struct dhcp6_packet* packet)
{
  struct sockaddr_in6 server_addr, client_addr;
  char response[1400];
  int sock = socket(PF_INET6, SOCK_DGRAM, 0);
  int i = 0;
  if (sock < 0)
    {
      perror("creating socket");
      return -1;
    }
  
    if (setsockopt(sock, SOL_SOCKET, 25, iface, strlen(iface)) == -1)
      {
        perror("SO_BINDTODEVICE");
        close(sock);
        return -1;
      }
    
    memset(&server_addr, 0, sizeof(server_addr));
    server_addr.sin6_family = AF_INET6;
    client_addr.sin6_family = AF_INET6;
    client_addr.sin6_port = htons(DHCP6_CLIENT_PORT);
    client_addr.sin6_flowinfo = 0;
    client_addr.sin6_scope_id =0;
    inet_pton(AF_INET6, "::", &client_addr.sin6_addr);
    bind(sock, (struct sockaddr*)&client_addr, sizeof(struct sockaddr_in6));
    inet_pton(AF_INET6, DHCP6_MULTICAST_ADDRESS, &server_addr.sin6_addr);
    server_addr.sin6_port = htons(DHCP6_SERVER_PORT);
    int16_t recv_size = 0;
    for (i = 0; i < 5; i++)
      {
        if (sendto(sock, packet->buf, packet->len, 0, (struct sockaddr *)&server_addr, sizeof(server_addr)) < 0)
	  {
	    perror("sendto failed");
            exit(4);
	  }
	
        recv_size = recvfrom(sock, response, sizeof(response), MSG_DONTWAIT, NULL, 0);
        if (recv_size == -1)
	  {
            if (errno == EAGAIN)
	      {
		sleep(1);
		continue;
	      }
	    else
	      {
                perror("recvfrom");
	      }
	  }
	
        int16_t result = parse_packet(response, recv_size);
        if (result == NOT_REPLY_CODE)
	  {
            sleep(1);
            continue;
	  }

        close(sock);
        return result;
      }

    close(sock);
    fprintf(stderr, "Response timed out\n");
    return -1;   
}


int main(int argc, char *  const argv[])
{
  const char* UNINITIALIZED = "";
  const char* iface = UNINITIALIZED;
  const char* ip = UNINITIALIZED;
  const char* client_id = UNINITIALIZED;
  const char* server_id = UNINITIALIZED;
  const char* iaid = UNINITIALIZED;
  int dry_run = 0;
  while (1)
    {
      int option_index = 0;
      int c = getopt_long(argc, argv, "a:s:c:n:i:hd", longopts, &option_index);
      if (c == -1)
	break;
        
      switch(c)
	{
	case 0:
	  if (longopts[option_index].flag !=0)
	    break;
	  
	  printf ("option %s", longopts[option_index].name);
	  if (optarg)
	    printf (" with arg %s", optarg);
	  printf ("\n");
	  break;

	case 'i':
	  iaid = optarg;
	  break;
	case 'n':
	  iface = optarg;
	  break;
	case 'a':
	  ip = optarg;
	  break;
	case 'c':
	  client_id = optarg;
	  break;
	case 'd':
	  dry_run = 1;
	  break;
	case 's':
	  server_id = optarg;
	  break;
	case 'h':
	  usage(argv[0], stdout);
	  return 0;
	case '?':
	  usage(argv[0], stderr);
	  return -1;
	default:
	  abort();
	  
        }
    }
  
  if (iaid == UNINITIALIZED)
    {
      fprintf(stderr, "Missing required iaid parameter\n");
      usage(argv[0], stderr);
      return -1;
    }
  
    if (server_id == UNINITIALIZED)
      {
        fprintf(stderr, "Missing required server-id parameter\n");
        usage(argv[0], stderr);
        return -1;
      }
    
    if (client_id == UNINITIALIZED)
      {
        fprintf(stderr, "Missing required client-id parameter\n");
        usage(argv[0], stderr);
        return -1;
      }
    
    if (ip == UNINITIALIZED)
      {
        fprintf(stderr, "Missing required ip parameter\n");
        usage(argv[0], stderr);
        return -1;
      }
    
    if (iface == UNINITIALIZED)
      {
	fprintf(stderr, "Missing required iface parameter\n");
        usage(argv[0], stderr);
        return -1;
      }

    
    
    struct dhcp6_packet packet = create_release_packet(iaid, ip, client_id, server_id);

    if (dry_run)
      {
        uint16_t i;

        for(i=0; i<packet.len; i++)
	  printf("%hhx", packet.buf[i]);
        
        printf("\n");
        return 0;
      }

    return send_release_packet(iface, &packet);
}
