/*
 * Copyright (c) 2017 Cisco and/or its affiliates.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at:
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include <vnet/dns/dns.h>

#include <vnet/vnet.h>
#include <vnet/fib/fib.h>
#include <vlibmemory/api.h>

#include <vnet/udp/udp.h>

#include <vnet/vnet_msg_enum.h>

#define vl_typedefs		/* define message structures */
#include <vnet/vnet_all_api_h.h>
#undef vl_typedefs

#define vl_endianfun		/* define message structures */
#include <vnet/vnet_all_api_h.h>
#undef vl_endianfun

/* instantiate all the print functions we know about */
#define vl_print(handle, ...) vlib_cli_output (handle, __VA_ARGS__)
#define vl_printfun
#include <vnet/vnet_all_api_h.h>
#undef vl_printfun

#include <vlibapi/api_helper_macros.h>

dns_main_t dns_main;

static int
dns_cache_clear (dns_main_t * dm)
{
  dns_cache_entry_t *ep;

  if (dm->is_enabled == 0)
    return VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED;

  dns_cache_lock (dm);

  /* *INDENT-OFF* */
  pool_foreach (ep, dm->entries,
  ({
    vec_free (ep->name);
    vec_free (ep->pending_api_requests);
    vec_free (ep->ip4_peers_to_notify);
    vec_free (ep->ip6_peers_to_notify);
  }));
  /* *INDENT-ON* */

  pool_free (dm->entries);
  hash_free (dm->cache_entry_by_name);
  dm->cache_entry_by_name = hash_create_string (0, sizeof (uword));
  vec_free (dm->unresolved_entries);
  dns_cache_unlock (dm);
  return 0;
}

static int
dns_enable_disable (dns_main_t * dm, int is_enable)
{
  vlib_thread_main_t *tm = &vlib_thread_main;
  u32 n_vlib_mains = tm->n_vlib_mains;

  if (is_enable)
    {
      if (vec_len (dm->ip4_name_servers) == 0
	  && (vec_len (dm->ip6_name_servers) == 0))
	return VNET_API_ERROR_NO_NAME_SERVERS;

      if (dm->cache_entry_by_name == 0)
	{
	  if (n_vlib_mains > 1)
	    dm->cache_lock = clib_mem_alloc_aligned (CLIB_CACHE_LINE_BYTES,
						     CLIB_CACHE_LINE_BYTES);

	  dm->cache_entry_by_name = hash_create_string (0, sizeof (uword));
	}

      dm->is_enabled = 1;
    }
  else
    {
      dns_cache_clear (dm);
      dm->is_enabled = 0;
    }
  return 0;
}

static void vl_api_dns_enable_disable_t_handler
  (vl_api_dns_enable_disable_t * mp)
{
  vl_api_dns_enable_disable_reply_t *rmp;
  dns_main_t *dm = &dns_main;
  int rv;

  rv = dns_enable_disable (dm, mp->enable);

  REPLY_MACRO (VL_API_DNS_ENABLE_DISABLE_REPLY);
}

static int
dns6_name_server_add_del (dns_main_t * dm,
			  u8 * server_address_as_u8, int is_add)
{
  int i;
  ip6_address_t *ap;

  if (is_add)
    {
      /* Already there? done... */
      for (i = 0; i < vec_len (dm->ip6_name_servers); i++)
	{
	  if (!memcmp (dm->ip6_name_servers + i, server_address_as_u8,
		       sizeof (ip6_address_t)))
	    return 0;
	}

      vec_add2 (dm->ip6_name_servers, ap, 1);
      clib_memcpy (ap, server_address_as_u8, sizeof (*ap));
    }
  else
    {
      for (i = 0; i < vec_len (dm->ip6_name_servers); i++)
	{
	  if (!memcmp (dm->ip6_name_servers + i, server_address_as_u8,
		       sizeof (ip6_address_t)))
	    {
	      vec_delete (dm->ip6_name_servers, 1, i);
	      return 0;
	    }
	}
      return VNET_API_ERROR_NAME_SERVER_NOT_FOUND;
    }
  return 0;
}

static int
dns4_name_server_add_del (dns_main_t * dm,
			  u8 * server_address_as_u8, int is_add)
{
  int i;
  ip4_address_t *ap;

  if (is_add)
    {
      /* Already there? done... */
      for (i = 0; i < vec_len (dm->ip4_name_servers); i++)
	{
	  if (!memcmp (dm->ip4_name_servers + i, server_address_as_u8,
		       sizeof (ip4_address_t)))
	    return 0;
	}

      vec_add2 (dm->ip4_name_servers, ap, 1);
      clib_memcpy (ap, server_address_as_u8, sizeof (*ap));
    }
  else
    {
      for (i = 0; i < vec_len (dm->ip4_name_servers); i++)
	{
	  if (!memcmp (dm->ip4_name_servers + i, server_address_as_u8,
		       sizeof (ip4_address_t)))
	    {
	      vec_delete (dm->ip4_name_servers, 1, i);
	      return 0;
	    }
	}
      return VNET_API_ERROR_NAME_SERVER_NOT_FOUND;
    }
  return 0;
}

static void vl_api_dns_name_server_add_del_t_handler
  (vl_api_dns_name_server_add_del_t * mp)
{
  dns_main_t *dm = &dns_main;
  vl_api_dns_name_server_add_del_reply_t *rmp;
  int rv;

  if (mp->is_ip6)
    rv = dns6_name_server_add_del (dm, mp->server_address, mp->is_add);
  else
    rv = dns4_name_server_add_del (dm, mp->server_address, mp->is_add);

  REPLY_MACRO (VL_API_DNS_NAME_SERVER_ADD_DEL_REPLY);
}

static void
send_dns4_request (dns_main_t * dm,
		   dns_cache_entry_t * ep, ip4_address_t * server)
{
  vlib_main_t *vm = dm->vlib_main;
  f64 now = vlib_time_now (vm);
  u32 bi;
  vlib_buffer_t *b;
  ip4_header_t *ip;
  fib_prefix_t prefix;
  fib_node_index_t fei;
  u32 sw_if_index, fib_index;
  udp_header_t *udp;
  ip4_main_t *im4 = &ip4_main;
  ip_lookup_main_t *lm4 = &im4->lookup_main;
  ip_interface_address_t *ia = 0;
  ip4_address_t *src_address;
  u8 *dns_request;
  vlib_frame_t *f;
  u32 *to_next;

  ASSERT (ep->dns_request);

  /* Find a FIB path to the server */
  clib_memcpy (&prefix.fp_addr.ip4, server, sizeof (*server));
  prefix.fp_proto = FIB_PROTOCOL_IP4;
  prefix.fp_len = 32;

  fib_index = fib_table_find (prefix.fp_proto, 0 /* default VRF for now */ );
  if (fib_index == (u32) ~ 0)
    {
      clib_warning ("no fib table");
      return;
    }

  fei = fib_table_lookup (fib_index, &prefix);

  /* Couldn't find route to destination. Bail out. */
  if (fei == FIB_NODE_INDEX_INVALID)
    {
      clib_warning ("no route to DNS server");
      return;
    }

  sw_if_index = fib_entry_get_resolving_interface (fei);

  if (sw_if_index == ~0)
    {
      clib_warning
	("route to %U exists, fei %d, get_resolving_interface returned"
	 " ~0", fei, format_ip4_address, &prefix.fp_addr);
      return;
    }

  /* *INDENT-OFF* */
  foreach_ip_interface_address(lm4, ia, sw_if_index, 1 /* honor unnummbered */,
  ({
    src_address = ip_interface_address_get_address (lm4, ia);
    goto found_src_address;
  }));
  /* *INDENT-ON* */

  clib_warning ("FIB BUG");
  return;

found_src_address:

  /* Go get a buffer */
  if (vlib_buffer_alloc (dm->vlib_main, &bi, 1) != 1)
    return;

  b = vlib_get_buffer (vm, bi);
  b->current_length = sizeof (ip4_header_t) + sizeof (udp_header_t) +
    vec_len (ep->dns_request);
  b->total_length_not_including_first_buffer = 0;
  b->flags =
    VLIB_BUFFER_TOTAL_LENGTH_VALID | VNET_BUFFER_F_LOCALLY_ORIGINATED;
  vnet_buffer (b)->sw_if_index[VLIB_RX] = 0;	/* "local0" */
  vnet_buffer (b)->sw_if_index[VLIB_TX] = 0;	/* default VRF for now */

  ip = vlib_buffer_get_current (b);
  memset (ip, 0, sizeof (*ip));
  udp = (udp_header_t *) (ip + 1);
  memset (udp, 0, sizeof (*udp));

  dns_request = (u8 *) (udp + 1);

  /* IP header */
  ip->ip_version_and_header_length = 0x45;
  ip->length = clib_host_to_net_u16 (vlib_buffer_length_in_chain (vm, b));
  ip->ttl = 255;
  ip->protocol = IP_PROTOCOL_UDP;
  ip->src_address.as_u32 = src_address->as_u32;
  ip->dst_address.as_u32 = server->as_u32;
  ip->checksum = ip4_header_checksum (ip);

  /* UDP header */
  udp->src_port = clib_host_to_net_u16 (UDP_DST_PORT_dns_reply);
  udp->dst_port = clib_host_to_net_u16 (UDP_DST_PORT_dns);
  udp->length = clib_host_to_net_u16 (sizeof (udp_header_t) +
				      vec_len (ep->dns_request));
  udp->checksum = 0;

  /* The actual DNS request */
  clib_memcpy (dns_request, ep->dns_request, vec_len (ep->dns_request));

  /* Ship it to ip4_lookup */
  f = vlib_get_frame_to_node (vm, ip4_lookup_node.index);
  to_next = vlib_frame_vector_args (f);
  to_next[0] = bi;
  f->n_vectors = 1;
  vlib_put_frame_to_node (vm, ip4_lookup_node.index, f);

  ep->retry_timer = now + 2.0;
}

static void
send_dns6_request (dns_main_t * dm,
		   dns_cache_entry_t * ep, ip6_address_t * server)
{
  vlib_main_t *vm = dm->vlib_main;
  f64 now = vlib_time_now (vm);
  u32 bi;
  vlib_buffer_t *b;
  ip6_header_t *ip;
  fib_prefix_t prefix;
  fib_node_index_t fei;
  u32 sw_if_index, fib_index;
  udp_header_t *udp;
  ip6_main_t *im6 = &ip6_main;
  ip_lookup_main_t *lm6 = &im6->lookup_main;
  ip_interface_address_t *ia = 0;
  ip6_address_t *src_address;
  u8 *dns_request;
  vlib_frame_t *f;
  u32 *to_next;
  int junk __attribute__ ((unused));

  ASSERT (ep->dns_request);

  /* Find a FIB path to the server */
  clib_memcpy (&prefix.fp_addr, server, sizeof (*server));
  prefix.fp_proto = FIB_PROTOCOL_IP6;
  prefix.fp_len = 32;

  fib_index = fib_table_find (prefix.fp_proto, 0 /* default VRF for now */ );
  if (fib_index == (u32) ~ 0)
    {
      clib_warning ("no fib table");
      return;
    }

  fei = fib_table_lookup (fib_index, &prefix);

  /* Couldn't find route to destination. Bail out. */
  if (fei == FIB_NODE_INDEX_INVALID)
    {
      clib_warning ("no route to DNS server");
    }

  sw_if_index = fib_entry_get_resolving_interface (fei);

  /* *INDENT-OFF* */
  foreach_ip_interface_address(lm6, ia, sw_if_index, 1 /* honor unnummbered */,
  ({
    src_address = ip_interface_address_get_address (lm6, ia);
    goto found_src_address;
  }));
  /* *INDENT-ON* */

  clib_warning ("FIB BUG");
  return;

found_src_address:

  /* Go get a buffer */
  if (vlib_buffer_alloc (dm->vlib_main, &bi, 1) != 1)
    return;

  b = vlib_get_buffer (vm, bi);
  b->current_length = sizeof (ip6_header_t) + sizeof (udp_header_t) +
    vec_len (ep->dns_request);
  b->total_length_not_including_first_buffer = 0;
  b->flags =
    VLIB_BUFFER_TOTAL_LENGTH_VALID | VNET_BUFFER_F_LOCALLY_ORIGINATED;

  ip = vlib_buffer_get_current (b);
  memset (ip, 0, sizeof (*ip));
  udp = (udp_header_t *) (ip + 1);
  memset (udp, 0, sizeof (*udp));

  dns_request = (u8 *) (udp + 1);

  /* IP header */
  ip->ip_version_traffic_class_and_flow_label =
    clib_host_to_net_u32 (0x6 << 28);

  ip->payload_length =
    clib_host_to_net_u16 (vlib_buffer_length_in_chain (vm, b)
			  - sizeof (ip6_header_t));
  ip->hop_limit = 255;
  ip->protocol = IP_PROTOCOL_UDP;
  clib_memcpy (&ip->src_address, src_address, sizeof (ip6_address_t));
  clib_memcpy (&ip->dst_address, server, sizeof (ip6_address_t));

  /* UDP header */
  udp->src_port = clib_host_to_net_u16 (UDP_DST_PORT_dns_reply);
  udp->dst_port = clib_host_to_net_u16 (UDP_DST_PORT_dns);
  udp->length = clib_host_to_net_u16 (sizeof (udp_header_t) +
				      vec_len (ep->dns_request));
  udp->checksum = 0;
  udp->checksum = ip6_tcp_udp_icmp_compute_checksum (vm, b, ip, &junk);

  /* The actual DNS request */
  clib_memcpy (dns_request, ep->dns_request, vec_len (ep->dns_request));

  /* Ship it to ip6_lookup */
  f = vlib_get_frame_to_node (vm, ip6_lookup_node.index);
  to_next = vlib_frame_vector_args (f);
  to_next[0] = bi;
  f->n_vectors = 1;

  ep->retry_timer = now + 2.0;
}

/**
 * Translate "foo.com" into "0x3 f o o 0x3 c o m 0x0"
 * A historical / hysterical micro-TLV scheme. DGMS.
 */
u8 *
name_to_labels (u8 * name)
{
  int i;
  int last_label_index;
  u8 *rv;

  rv = vec_dup (name);

  /* punch in space for the first length */
  vec_insert (rv, 1, 0);
  last_label_index = 0;
  i = 1;

  while (i < vec_len (rv))
    {
      if (rv[i] == '.')
	{
	  rv[last_label_index] = (i - last_label_index) - 1;
	  if ((i - last_label_index) > 63)
	    clib_warning ("stupid name, label length %d",
			  i - last_label_index);
	  last_label_index = i;
	  rv[i] = 0;
	}
      i++;
    }
  /* Set the last real label length */
  rv[last_label_index] = (i - last_label_index) - 1;

  /*
   * Add a [sic] NULL root label. Otherwise, the name parser can't figure out
   * where to stop.
   */
  vec_add1 (rv, 0);
  return rv;
}

/**
 * arc-function for the above.
 * Translate "0x3 f o o 0x3 c o m 0x0" into "foo.com"
 * Produces a non-NULL-terminated u8 *vector. %v format is your friend.
 */
u8 *
labels_to_name (u8 * label, u8 * full_text, u8 ** parse_from_here)
{
  u8 *reply = 0;
  u16 offset;
  u8 len;
  int i;

  *parse_from_here = 0;

  /* chase initial pointer? */
  if ((label[0] & 0xC0) == 0xC0)
    {
      *parse_from_here = label + 2;
      offset = ((label[0] & 0x3f) << 8) + label[1];
      label = full_text + offset;
    }

  len = *label++;

  while (len)
    {
      for (i = 0; i < len; i++)
	vec_add1 (reply, *label++);

      /* chase pointer? */
      if ((label[0] & 0xC0) == 0xC0)
	{
	  *parse_from_here = label + 2;
	  offset = ((label[0] & 0x3f) << 8) + label[1];
	  label = full_text + offset;
	}

      len = *label++;
      if (len)
	vec_add1 (reply, '.');
    }
  if (*parse_from_here == 0)
    *parse_from_here = label;
  return reply;
}

void
vnet_send_dns_request (dns_main_t * dm, dns_cache_entry_t * ep)
{
  dns_header_t *h;
  dns_query_t *qp;
  u16 tmp;
  u8 *request;
  u32 qp_offset;

  /* This can easily happen if sitting in GDB, etc. */
  if (ep->flags & DNS_CACHE_ENTRY_FLAG_VALID)
    return;

  /* Construct the dns request, if we haven't been here already */
  if (vec_len (ep->dns_request) == 0)
    {
      /*
       * Start with the variadic portion of the exercise.
       * Turn the name into a set of DNS "labels". Max length
       * per label is 63, enforce that.
       */
      request = name_to_labels (ep->name);
      qp_offset = vec_len (request);

      /* Add space for the query header */
      vec_validate (request, qp_offset + sizeof (dns_query_t) - 1);

      qp = (dns_query_t *) (request + qp_offset);

      qp->type = clib_host_to_net_u16 (DNS_TYPE_ALL);
      qp->class = clib_host_to_net_u16 (DNS_CLASS_IN);

      /* Punch in space for the dns_header_t */
      vec_insert (request, sizeof (dns_header_t), 0);

      h = (dns_header_t *) request;

      /* Transaction ID = pool index */
      h->id = clib_host_to_net_u16 (ep - dm->entries);

      /* Ask for a recursive lookup */
      tmp = DNS_RD | DNS_OPCODE_QUERY;
      h->flags = clib_host_to_net_u16 (tmp);
      h->qdcount = clib_host_to_net_u16 (1);
      h->nscount = 0;
      h->arcount = 0;

      ep->dns_request = request;
    }

  /* Work out which server / address family we're going to use */

  /* Retry using current server */
  if (ep->retry_count++ < DNS_RETRIES_PER_SERVER)
    {
      if (ep->server_af == 1 /* ip6 */ )
	{
	  if (vec_len (dm->ip6_name_servers))
	    {
	      send_dns6_request (dm, ep,
				 dm->ip6_name_servers + ep->server_rotor);
	      goto out;
	    }
	  else
	    ep->server_af = 0;
	}
      if (vec_len (dm->ip4_name_servers))
	{
	  send_dns4_request (dm, ep, dm->ip4_name_servers + ep->server_rotor);
	  goto out;
	}
    }
  else				/* switch to a new server */
    {
      ep->retry_count = 1;
      ep->server_rotor++;
      if (ep->server_af == 1 /* ip6 */ )
	{
	  if (ep->server_rotor >= vec_len (dm->ip6_name_servers))
	    {
	      ep->server_rotor = 0;
	      ep->server_af = vec_len (dm->ip4_name_servers) > 0 ? 0 : 1;
	    }
	}
      else
	{
	  if (ep->server_rotor >= vec_len (dm->ip4_name_servers))
	    {
	      ep->server_rotor = 0;
	      ep->server_af = vec_len (dm->ip6_name_servers) > 0 ? 1 : 0;
	    }
	}
    }

  if (ep->server_af == 1 /* ip6 */ )
    send_dns6_request (dm, ep, dm->ip6_name_servers + ep->server_rotor);
  else
    send_dns4_request (dm, ep, dm->ip4_name_servers + ep->server_rotor);

out:

  vlib_process_signal_event_mt (dm->vlib_main, dns_resolver_node.index,
				DNS_RESOLVER_EVENT_PENDING, 0);
}

int
vnet_dns_delete_entry_by_index_nolock (dns_main_t * dm, u32 index)
{
  dns_cache_entry_t *ep;
  int i;

  if (dm->is_enabled == 0)
    return VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED;

  if (pool_is_free_index (dm->entries, index))
    return VNET_API_ERROR_NO_SUCH_ENTRY;

  ep = pool_elt_at_index (dm->entries, index);
  if (!(ep->flags & DNS_CACHE_ENTRY_FLAG_VALID))
    {
      for (i = 0; i < vec_len (dm->unresolved_entries); i++)
	if (index == dm->unresolved_entries[i])
	  {
	    vec_delete (dm->unresolved_entries, 1, i);
	    goto found;
	  }
      clib_warning ("pool elt %d supposedly pending, but not found...",
		    index);
    }

found:
  hash_unset_mem (dm->cache_entry_by_name, ep->name);
  vec_free (ep->name);
  vec_free (ep->pending_api_requests);
  vec_free (ep->ip4_peers_to_notify);
  vec_free (ep->ip6_peers_to_notify);
  pool_put (dm->entries, ep);

  return 0;
}

static int
dns_delete_by_name (dns_main_t * dm, u8 * name)
{
  int rv;
  uword *p;

  if (dm->is_enabled == 0)
    return VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED;

  dns_cache_lock (dm);
  p = hash_get_mem (dm->cache_entry_by_name, name);
  if (!p)
    {
      dns_cache_unlock (dm);
      return VNET_API_ERROR_NO_SUCH_ENTRY;
    }
  rv = vnet_dns_delete_entry_by_index_nolock (dm, p[0]);

  dns_cache_unlock (dm);

  return rv;
}

static int
delete_random_entry (dns_main_t * dm)
{
  int rv;
  u32 victim_index, start_index, i;
  u32 limit;
  dns_cache_entry_t *ep;

  if (dm->is_enabled == 0)
    return VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED;

  /*
   * Silence spurious coverity warning. We know pool_elts >> 0, or
   * we wouldn't be here...
   */
#ifdef __COVERITY__
  if (pool_elts (dm->entries) == 0)
    return VNET_API_ERROR_UNSPECIFIED;
#endif

  dns_cache_lock (dm);
  limit = pool_elts (dm->entries);
  start_index = random_u32 (&dm->random_seed) % limit;

  for (i = 0; i < limit; i++)
    {
      victim_index = (start_index + i) % limit;

      if (!pool_is_free_index (dm->entries, victim_index))
	{
	  ep = pool_elt_at_index (dm->entries, victim_index);
	  /* Delete only valid, non-static entries */
	  if ((ep->flags & DNS_CACHE_ENTRY_FLAG_VALID)
	      && ((ep->flags & DNS_CACHE_ENTRY_FLAG_STATIC) == 0))
	    {
	      rv = vnet_dns_delete_entry_by_index_nolock (dm, victim_index);
	      dns_cache_unlock (dm);
	      return rv;
	    }
	}
    }
  dns_cache_unlock (dm);

  clib_warning ("Couldn't find an entry to delete?");
  return VNET_API_ERROR_UNSPECIFIED;
}

static int
dns_add_static_entry (dns_main_t * dm, u8 * name, u8 * dns_reply_data)
{
  dns_cache_entry_t *ep;
  uword *p;
  int rv;

  if (dm->is_enabled == 0)
    return VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED;

  dns_cache_lock (dm);
  p = hash_get_mem (dm->cache_entry_by_name, name);
  if (p)
    {
      dns_cache_unlock (dm);
      return VNET_API_ERROR_ENTRY_ALREADY_EXISTS;
    }

  if (pool_elts (dm->entries) == dm->name_cache_size)
    {
      /* Will only fail if the cache is totally filled w/ static entries... */
      rv = delete_random_entry (dm);
      if (rv)
	{
	  dns_cache_unlock (dm);
	  return rv;
	}
    }

  pool_get (dm->entries, ep);
  memset (ep, 0, sizeof (*ep));

  /* Note: consumes the name vector */
  ep->name = name;
  hash_set_mem (dm->cache_entry_by_name, ep->name, ep - dm->entries);
  ep->flags = DNS_CACHE_ENTRY_FLAG_VALID | DNS_CACHE_ENTRY_FLAG_STATIC;
  ep->dns_response = dns_reply_data;

  dns_cache_unlock (dm);
  return 0;
}

static int
dns_resolve_name (dns_main_t * dm,
		  u8 * name, u32 client_index, u32 client_context,
		  u32 request_type, dns_cache_entry_t ** retp)
{
  dns_cache_entry_t *ep;
  int rv;
  f64 now;
  uword *p;
  pending_api_request_t *pr;

  now = vlib_time_now (dm->vlib_main);

  /* In case we can't actually answer the question right now... */
  *retp = 0;

  dns_cache_lock (dm);
search_again:
  p = hash_get_mem (dm->cache_entry_by_name, name);
  if (p)
    {
      ep = pool_elt_at_index (dm->entries, p[0]);
      if (ep->flags & DNS_CACHE_ENTRY_FLAG_VALID)
	{
	  /* Has the entry expired? */
	  if (((ep->flags & DNS_CACHE_ENTRY_FLAG_STATIC) == 0)
	      && (now > ep->expiration_time))
	    {
	      int i;
	      u32 *indices_to_delete = 0;

	      /*
	       * Take out the rest of the resolution chain
	       * This isn't optimal, but it won't happen very often.
	       */
	      while (ep)
		{
		  if ((ep->flags & DNS_CACHE_ENTRY_FLAG_CNAME))
		    {
		      vec_add1 (indices_to_delete, ep - dm->entries);

		      p = hash_get_mem (dm->cache_entry_by_name, ep->cname);
		      if (!p)
			break;
		      ep = pool_elt_at_index (dm->entries, p[0]);
		    }
		  else
		    {
		      vec_add1 (indices_to_delete, ep - dm->entries);
		      break;
		    }
		}
	      for (i = 0; i < vec_len (indices_to_delete); i++)
		{
		  /* Reenable to watch re-resolutions */
		  if (0)
		    {
		      ep = pool_elt_at_index (dm->entries,
					      indices_to_delete[i]);
		      clib_warning ("Re-resolve %s", ep->name);
		    }

		  vnet_dns_delete_entry_by_index_nolock
		    (dm, indices_to_delete[i]);
		}
	      vec_free (indices_to_delete);
	      /* Yes, kill it... */
	      goto re_resolve;
	    }

	  if (ep->flags & DNS_CACHE_ENTRY_FLAG_CNAME)
	    {
	      name = ep->cname;
	      goto search_again;
	    }

	  /* Note: caller must drop the lock! */
	  *retp = ep;
	  return (0);
	}
      else
	{
	  /*
	   * Resolution pending. Add request to the pending vector
	   */
	  vec_add2 (ep->pending_api_requests, pr, 1);
	  pr->request_type = request_type;
	  pr->client_index = client_index;
	  pr->client_context = client_context;
	  dns_cache_unlock (dm);
	  return (0);
	}
    }

re_resolve:
  if (pool_elts (dm->entries) == dm->name_cache_size)
    {
      /* Will only fail if the cache is totally filled w/ static entries... */
      rv = delete_random_entry (dm);
      if (rv)
	{
	  dns_cache_unlock (dm);
	  return rv;
	}
    }

  /* add new hash table entry */
  pool_get (dm->entries, ep);
  memset (ep, 0, sizeof (*ep));

  ep->name = format (0, "%s%c", name, 0);
  _vec_len (ep->name) = vec_len (ep->name) - 1;

  hash_set_mem (dm->cache_entry_by_name, ep->name, ep - dm->entries);

  vec_add1 (dm->unresolved_entries, ep - dm->entries);
  vec_add2 (ep->pending_api_requests, pr, 1);
  pr->request_type = request_type;
  pr->client_index = client_index;
  pr->client_context = client_context;
  vnet_send_dns_request (dm, ep);
  dns_cache_unlock (dm);
  return 0;
}

#define foreach_notification_to_move            \
_(pending_api_requests)				\
_(ip4_peers_to_notify)                          \
_(ip6_peers_to_notify)

/**
 * Handle cname indirection. JFC. Called with the cache locked.
 * returns 0 if the reply is not a CNAME.
 */

int
vnet_dns_cname_indirection_nolock (dns_main_t * dm, u32 ep_index, u8 * reply)
{
  dns_header_t *h;
  dns_query_t *qp;
  dns_rr_t *rr;
  u8 *curpos;
  u8 *pos, *pos2;
  int len, i;
  u8 *cname = 0;
  u8 *request = 0;
  u32 qp_offset;
  u16 flags;
  u16 rcode;
  dns_cache_entry_t *ep, *next_ep;
  f64 now;

  h = (dns_header_t *) reply;
  flags = clib_net_to_host_u16 (h->flags);
  rcode = flags & DNS_RCODE_MASK;

  /* See if the response is OK */
  switch (rcode)
    {
    case DNS_RCODE_NO_ERROR:
      break;

    case DNS_RCODE_NAME_ERROR:
    case DNS_RCODE_FORMAT_ERROR:
    case DNS_RCODE_SERVER_FAILURE:
    case DNS_RCODE_NOT_IMPLEMENTED:
    case DNS_RCODE_REFUSED:
      return 0;
    }

  curpos = (u8 *) (h + 1);
  pos = curpos;
  len = *pos++;

  /* Skip the questions */
  for (i = 0; i < clib_net_to_host_u16 (h->qdcount); i++)
    {
      while (len)
	{
	  pos += len;
	  len = *pos++;
	}
      pos += sizeof (dns_query_t);
    }
  pos2 = pos;
  /* expect a pointer chase here for a CNAME record */
  if ((pos2[0] & 0xC0) == 0xC0)
    pos += 2;
  else
    return 0;

  rr = (dns_rr_t *) pos;

  /* This is a real record, not a CNAME record */
  if (clib_net_to_host_u16 (rr->type) != DNS_TYPE_CNAME)
    return 0;

  /* This is a CNAME record, chase the name chain. */

  /* The last request is no longer pending.. */
  for (i = 0; i < vec_len (dm->unresolved_entries); i++)
    if (ep_index == dm->unresolved_entries[i])
      {
	vec_delete (dm->unresolved_entries, 1, i);
	goto found_last_request;
      }
  clib_warning ("pool elt %d supposedly pending, but not found...", ep_index);

found_last_request:

  now = vlib_time_now (dm->vlib_main);
  cname = labels_to_name (rr->rdata, reply, &pos2);
  /* Save the cname */
  vec_add1 (cname, 0);
  _vec_len (cname) -= 1;
  ep = pool_elt_at_index (dm->entries, ep_index);
  ep->cname = cname;
  ep->flags |= (DNS_CACHE_ENTRY_FLAG_CNAME | DNS_CACHE_ENTRY_FLAG_VALID);
  /* Save the response */
  ep->dns_response = reply;
  /* Set up expiration time */
  ep->expiration_time = now + clib_net_to_host_u32 (rr->ttl);

  pool_get (dm->entries, next_ep);

  /* Need to recompute ep post pool-get */
  ep = pool_elt_at_index (dm->entries, ep_index);

  memset (next_ep, 0, sizeof (*next_ep));
  next_ep->name = vec_dup (cname);
  vec_add1 (next_ep->name, 0);
  _vec_len (next_ep->name) -= 1;

  hash_set_mem (dm->cache_entry_by_name, next_ep->name,
		next_ep - dm->entries);

  /* Use the same server */
  next_ep->server_rotor = ep->server_rotor;
  next_ep->server_af = ep->server_af;

  /* Move notification data to the next name in the chain */
#define _(a) next_ep->a = ep->a; ep->a = 0;
  foreach_notification_to_move;
#undef _

  request = name_to_labels (cname);

  qp_offset = vec_len (request);

  /* Add space for the query header */
  vec_validate (request, qp_offset + sizeof (dns_query_t) - 1);

  qp = (dns_query_t *) (request + qp_offset);

  qp->type = clib_host_to_net_u16 (DNS_TYPE_ALL);
  qp->class = clib_host_to_net_u16 (DNS_CLASS_IN);

  /* Punch in space for the dns_header_t */
  vec_insert (request, sizeof (dns_header_t), 0);

  h = (dns_header_t *) request;

  /* Transaction ID = pool index */
  h->id = clib_host_to_net_u16 (next_ep - dm->entries);

  /* Ask for a recursive lookup */
  h->flags = clib_host_to_net_u16 (DNS_RD | DNS_OPCODE_QUERY);
  h->qdcount = clib_host_to_net_u16 (1);
  h->nscount = 0;
  h->arcount = 0;

  next_ep->dns_request = request;
  next_ep->retry_timer = now + 2.0;
  next_ep->retry_count = 0;

  /*
   * Enable this to watch recursive resolution happen...
   * fformat (stdout, "%U", format_dns_reply, request, 2);
   */

  vec_add1 (dm->unresolved_entries, next_ep - dm->entries);
  vnet_send_dns_request (dm, next_ep);
  return (1);
}

int
vnet_dns_response_to_reply (u8 * response,
			    vl_api_dns_resolve_name_reply_t * rmp,
			    u32 * min_ttlp)
{
  dns_header_t *h;
  dns_query_t *qp;
  dns_rr_t *rr;
  int i, limit;
  u8 len;
  u8 *curpos, *pos;
  u16 flags;
  u16 rcode;
  u32 ttl;

  h = (dns_header_t *) response;
  flags = clib_net_to_host_u16 (h->flags);
  rcode = flags & DNS_RCODE_MASK;

  /* See if the response is OK, etc. */
  switch (rcode)
    {
    default:
    case DNS_RCODE_NO_ERROR:
      break;

    case DNS_RCODE_NAME_ERROR:
    case DNS_RCODE_FORMAT_ERROR:
      return VNET_API_ERROR_NAME_SERVER_NO_SUCH_NAME;

    case DNS_RCODE_SERVER_FAILURE:
    case DNS_RCODE_NOT_IMPLEMENTED:
    case DNS_RCODE_REFUSED:
      return VNET_API_ERROR_NAME_SERVER_NEXT_SERVER;
    }

  /* No answers? Loser... */
  if (clib_net_to_host_u16 (h->anscount) < 1)
    return VNET_API_ERROR_NAME_SERVER_NO_ADDRESSES;

  curpos = (u8 *) (h + 1);

  /* Skip the name we asked about */
  pos = curpos;
  len = *pos++;
  /* Should never happen, but stil... */
  if ((len & 0xC0) == 0xC0)
    curpos += 2;
  else
    {
      /* skip the name / label-set */
      while (len)
	{
	  pos += len;
	  len = *pos++;
	}
      curpos = pos;
    }
  /* Skip queries */
  limit = clib_net_to_host_u16 (h->qdcount);
  qp = (dns_query_t *) curpos;
  qp += limit;
  curpos = (u8 *) qp;

  /* Parse answers */
  limit = clib_net_to_host_u16 (h->anscount);

  for (i = 0; i < limit; i++)
    {
      pos = curpos;

      /* Expect pointer chases in the answer section... */
      if ((pos[0] & 0xC0) == 0xC0)
	curpos += 2;
      else
	{
	  len = *pos++;
	  while (len)
	    {
	      if ((pos[0] & 0xC0) == 0xC0)
		{
		  curpos = pos + 2;
		  goto curpos_set;
		}
	      pos += len;
	      len = *pos++;
	    }
	  curpos = pos;
	}

    curpos_set:
      rr = (dns_rr_t *) curpos;

      switch (clib_net_to_host_u16 (rr->type))
	{
	case DNS_TYPE_A:
	  /* Collect an ip4 address. Do not pass go. Do not collect $200 */
	  memcpy (rmp->ip4_address, rr->rdata, sizeof (ip4_address_t));
	  rmp->ip4_set = 1;
	  ttl = clib_net_to_host_u32 (rr->ttl);
	  if (min_ttlp && *min_ttlp > ttl)
	    *min_ttlp = ttl;
	  break;
	case DNS_TYPE_AAAA:
	  /* Collect an ip6 address. Do not pass go. Do not collect $200 */
	  memcpy (rmp->ip6_address, rr->rdata, sizeof (ip6_address_t));
	  ttl = clib_net_to_host_u32 (rr->ttl);
	  if (min_ttlp && *min_ttlp > ttl)
	    *min_ttlp = ttl;
	  rmp->ip6_set = 1;
	  break;
	default:
	  break;
	}
      /* Might as well stop ASAP */
      if (rmp->ip4_set && rmp->ip6_set)
	break;
      curpos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
    }

  if ((rmp->ip4_set + rmp->ip6_set) == 0)
    return VNET_API_ERROR_NAME_SERVER_NO_ADDRESSES;
  return 0;
}

int
vnet_dns_response_to_name (u8 * response,
			   vl_api_dns_resolve_ip_reply_t * rmp,
			   u32 * min_ttlp)
{
  dns_header_t *h;
  dns_query_t *qp;
  dns_rr_t *rr;
  int i, limit;
  u8 len;
  u8 *curpos, *pos;
  u16 flags;
  u16 rcode;
  u8 *name;
  u32 ttl;
  u8 *junk __attribute__ ((unused));
  int name_set = 0;

  h = (dns_header_t *) response;
  flags = clib_net_to_host_u16 (h->flags);
  rcode = flags & DNS_RCODE_MASK;

  /* See if the response is OK, etc. */
  switch (rcode)
    {
    default:
    case DNS_RCODE_NO_ERROR:
      break;

    case DNS_RCODE_NAME_ERROR:
    case DNS_RCODE_FORMAT_ERROR:
      return VNET_API_ERROR_NAME_SERVER_NO_SUCH_NAME;

    case DNS_RCODE_SERVER_FAILURE:
    case DNS_RCODE_NOT_IMPLEMENTED:
    case DNS_RCODE_REFUSED:
      return VNET_API_ERROR_NAME_SERVER_NEXT_SERVER;
    }

  /* No answers? Loser... */
  if (clib_net_to_host_u16 (h->anscount) < 1)
    return VNET_API_ERROR_NAME_SERVER_NO_ADDRESSES;

  curpos = (u8 *) (h + 1);

  /* Skip the name we asked about */
  pos = curpos;
  len = *pos++;
  /* Should never happen, but stil... */
  if ((len & 0xC0) == 0xC0)
    curpos += 2;
  else
    {
      /* skip the name / label-set */
      while (len)
	{
	  pos += len;
	  len = *pos++;
	}
      curpos = pos;
    }
  /* Skip queries */
  limit = clib_net_to_host_u16 (h->qdcount);
  qp = (dns_query_t *) curpos;
  qp += limit;
  curpos = (u8 *) qp;

  /* Parse answers */
  limit = clib_net_to_host_u16 (h->anscount);

  for (i = 0; i < limit; i++)
    {
      pos = curpos;

      /* Expect pointer chases in the answer section... */
      if ((pos[0] & 0xC0) == 0xC0)
	curpos += 2;
      else
	{
	  len = *pos++;
	  while (len)
	    {
	      if ((pos[0] & 0xC0) == 0xC0)
		{
		  curpos = pos + 2;
		  goto curpos_set;
		}
	      pos += len;
	      len = *pos++;
	    }
	  curpos = pos;
	}

    curpos_set:
      rr = (dns_rr_t *) curpos;

      switch (clib_net_to_host_u16 (rr->type))
	{
	case DNS_TYPE_PTR:
	  name = labels_to_name (rr->rdata, response, &junk);
	  memcpy (rmp->name, name, vec_len (name));
	  ttl = clib_net_to_host_u32 (rr->ttl);
	  if (*min_ttlp)
	    *min_ttlp = ttl;
	  rmp->name[vec_len (name)] = 0;
	  name_set = 1;
	  break;
	default:
	  break;
	}
      /* Might as well stop ASAP */
      if (name_set == 1)
	break;
      curpos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
    }

  if (name_set == 0)
    return VNET_API_ERROR_NAME_SERVER_NO_SUCH_NAME;
  return 0;
}

static void
vl_api_dns_resolve_name_t_handler (vl_api_dns_resolve_name_t * mp)
{
  dns_main_t *dm = &dns_main;
  vl_api_dns_resolve_name_reply_t *rmp;
  dns_cache_entry_t *ep;
  int rv;

  /* Sanitize the name slightly */
  mp->name[ARRAY_LEN (mp->name) - 1] = 0;

  rv = dns_resolve_name (dm, mp->name, mp->client_index, mp->context,
			 DNS_API_PENDING_NAME_TO_IP, &ep);

  /* Error, e.g. not enabled? Tell the user */
  if (rv < 0)
    {
      REPLY_MACRO (VL_API_DNS_RESOLVE_NAME_REPLY);
      return;
    }

  /* Resolution pending? Don't reply... */
  if (ep == 0)
    return;

  /* *INDENT-OFF* */
  REPLY_MACRO2(VL_API_DNS_RESOLVE_NAME_REPLY,
  ({
    rv = vnet_dns_response_to_reply (ep->dns_response, rmp, 0 /* ttl-ptr */);
    rmp->retval = clib_host_to_net_u32 (rv);
  }));
  /* *INDENT-ON* */

  /*
   * dns_resolve_name leaves the cache locked when it returns
   * a cached result, so unlock it here.
   */
  dns_cache_unlock (dm);
}

static void
vl_api_dns_resolve_ip_t_handler (vl_api_dns_resolve_ip_t * mp)
{
  dns_main_t *dm = &dns_main;
  vl_api_dns_resolve_ip_reply_t *rmp;
  dns_cache_entry_t *ep;
  int rv;
  int i, len;
  u8 *lookup_name = 0;
  u8 digit, nybble;

  if (mp->is_ip6)
    {
      for (i = 15; i >= 0; i--)
	{
	  digit = mp->address[i];
	  nybble = (digit & 0x0F);
	  if (nybble > 9)
	    vec_add1 (lookup_name, (nybble - 10) + 'a');
	  else
	    vec_add1 (lookup_name, nybble + '0');
	  vec_add1 (lookup_name, '.');
	  nybble = (digit & 0xF0) >> 4;
	  if (nybble > 9)
	    vec_add1 (lookup_name, (nybble - 10) + 'a');
	  else
	    vec_add1 (lookup_name, nybble + '0');
	  vec_add1 (lookup_name, '.');
	}
      len = vec_len (lookup_name);
      vec_validate (lookup_name, len + 8);
      memcpy (lookup_name + len, "ip6.arpa", 8);
    }
  else
    {
      for (i = 3; i >= 0; i--)
	{
	  digit = mp->address[i];
	  lookup_name = format (lookup_name, "%d.", digit);
	}
      lookup_name = format (lookup_name, "in-addr.arpa");
    }

  vec_add1 (lookup_name, 0);

  rv = dns_resolve_name (dm, lookup_name, mp->client_index, mp->context,
			 DNS_API_PENDING_IP_TO_NAME, &ep);

  vec_free (lookup_name);

  /* Error, e.g. not enabled? Tell the user */
  if (rv < 0)
    {
      REPLY_MACRO (VL_API_DNS_RESOLVE_IP_REPLY);
      return;
    }

  /* Resolution pending? Don't reply... */
  if (ep == 0)
    return;

  /* *INDENT-OFF* */
  REPLY_MACRO2(VL_API_DNS_RESOLVE_IP_REPLY,
  ({
    rv = vnet_dns_response_to_name (ep->dns_response, rmp, 0 /* ttl-ptr */);
    rmp->retval = clib_host_to_net_u32 (rv);
  }));
  /* *INDENT-ON* */

  /*
   * dns_resolve_name leaves the cache locked when it returns
   * a cached result, so unlock it here.
   */
  dns_cache_unlock (dm);
}

#define vl_msg_name_crc_list
#include <vpp/api/vpe_all_api_h.h>
#undef vl_msg_name_crc_list

static void
setup_message_id_table (api_main_t * am)
{
#define _(id,n,crc) vl_msg_api_add_msg_name_crc (am, #n "_" #crc, id);
  foreach_vl_msg_name_crc_dns;
#undef _
}

#define foreach_dns_api_msg                             \
_(DNS_ENABLE_DISABLE, dns_enable_disable)               \
_(DNS_NAME_SERVER_ADD_DEL, dns_name_server_add_del)     \
_(DNS_RESOLVE_NAME, dns_resolve_name)			\
_(DNS_RESOLVE_IP, dns_resolve_ip)

static clib_error_t *
dns_api_hookup (vlib_main_t * vm)
{
#define _(N,n)                                                  \
    vl_msg_api_set_handlers(VL_API_##N, #n,                     \
                           vl_api_##n##_t_handler,              \
                           vl_noop_handler,                     \
                           vl_api_##n##_t_endian,               \
                           vl_api_##n##_t_print,                \
                           sizeof(vl_api_##n##_t), 1);
  foreach_dns_api_msg;
#undef _

  setup_message_id_table (&api_main);
  return 0;
}

VLIB_API_INIT_FUNCTION (dns_api_hookup);


static clib_error_t *
dns_config_fn (vlib_main_t * vm, unformat_input_t * input)
{
  dns_main_t *dm = &dns_main;

  while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
    {
      if (unformat (input, "max-cache-size %u", &dm->name_cache_size))
	;
      else if (unformat (input, "max-ttl %u", &dm->max_ttl_in_seconds))
	;
      else
	return clib_error_return (0, "unknown input `%U'",
				  format_unformat_error, input);
    }
  return 0;
}

VLIB_CONFIG_FUNCTION (dns_config_fn, "dns");

static clib_error_t *
dns_init (vlib_main_t * vm)
{
  dns_main_t *dm = &dns_main;

  dm->vlib_main = vm;
  dm->vnet_main = vnet_get_main ();
  dm->name_cache_size = 65535;
  dm->max_ttl_in_seconds = 86400;
  dm->random_seed = 0xDEADDABE;

  udp_register_dst_port (vm, UDP_DST_PORT_dns_reply, dns46_reply_node.index,
			 1 /* is_ip4 */ );

  udp_register_dst_port (vm, UDP_DST_PORT_dns_reply6, dns46_reply_node.index,
			 0 /* is_ip4 */ );

#if 0
  udp_register_dst_port (vm, UDP_DST_PORT_dns, dns4_request_node.index,
			 1 /* is_ip4 */ );
  udp_register_dst_port (vm, UDP_DST_PORT_dns6, dns6_request_node.index,
			 0 /* is_ip4 */ );
#endif

  return 0;
}

VLIB_INIT_FUNCTION (dns_init);

uword
unformat_dns_reply (unformat_input_t * input, va_list * args)
{
  u8 **result = va_arg (*args, u8 **);
  u8 **namep = va_arg (*args, u8 **);
  ip4_address_t a4;
  ip6_address_t a6;
  int a4_set = 0;
  int a6_set = 0;
  u8 *name;
  int name_set = 0;
  u8 *ce;
  u32 qp_offset;
  dns_header_t *h;
  dns_query_t *qp;
  dns_rr_t *rr;
  u8 *rru8;

  if (unformat (input, "%v", &name))
    name_set = 1;

  if (unformat (input, "%U", unformat_ip4_address, &a4))
    {
      a4_set = 1;
      if (unformat (input, "%U", unformat_ip6_address, &a6))
	a6_set = 1;
    }

  if (unformat (input, "%U", unformat_ip6_address, &a6))
    {
      a6_set = 1;
      if (unformat (input, "%U", unformat_ip4_address, &a6))
	a4_set = 1;
    }

  /* Must have a name */
  if (!name_set)
    return 0;

  /* Must have at least one address */
  if (!(a4_set + a6_set))
    return 0;

  /* Build a fake DNS cache entry string, one hemorrhoid at a time */
  ce = name_to_labels (name);
  qp_offset = vec_len (ce);

  /* Add space for the query header */
  vec_validate (ce, qp_offset + sizeof (dns_query_t) - 1);
  qp = (dns_query_t *) (ce + qp_offset);

  qp->type = clib_host_to_net_u16 (DNS_TYPE_ALL);
  qp->class = clib_host_to_net_u16 (DNS_CLASS_IN);

  /* Punch in space for the dns_header_t */
  vec_insert (ce, sizeof (dns_header_t), 0);

  h = (dns_header_t *) ce;

  /* Fake Transaction ID */
  h->id = 0xFFFF;

  h->flags = clib_host_to_net_u16 (DNS_RD | DNS_RA);
  h->qdcount = clib_host_to_net_u16 (1);
  h->anscount = clib_host_to_net_u16 (a4_set + a6_set);
  h->nscount = 0;
  h->arcount = 0;

  /* Now append one or two A/AAAA RR's... */
  if (a4_set)
    {
      /* Pointer to the name (DGMS) */
      vec_add1 (ce, 0xC0);
      vec_add1 (ce, 0x0C);
      vec_add2 (ce, rru8, sizeof (*rr) + 4);
      rr = (void *) rru8;
      rr->type = clib_host_to_net_u16 (DNS_TYPE_A);
      rr->class = clib_host_to_net_u16 (DNS_CLASS_IN);
      rr->ttl = clib_host_to_net_u32 (86400);
      rr->rdlength = clib_host_to_net_u16 (4);
      memcpy (rr->rdata, &a4, sizeof (a4));
    }
  if (a6_set)
    {
      /* Pointer to the name (DGMS) */
      vec_add1 (ce, 0xC0);
      vec_add1 (ce, 0x0C);
      vec_add2 (ce, rru8, sizeof (*rr) + 16);
      rr = (void *) rru8;
      rr->type = clib_host_to_net_u16 (DNS_TYPE_AAAA);
      rr->class = clib_host_to_net_u16 (DNS_CLASS_IN);
      rr->ttl = clib_host_to_net_u32 (86400);
      rr->rdlength = clib_host_to_net_u16 (16);
      memcpy (rr->rdata, &a6, sizeof (a6));
    }
  *result = ce;
  if (namep)
    *namep = name;
  else
    vec_free (name);

  return 1;
}

u8 *
format_dns_query (u8 * s, va_list * args)
{
  u8 **curpos = va_arg (*args, u8 **);
  int verbose = va_arg (*args, int);
  u8 *pos;
  dns_query_t *qp;
  int len, i;
  if (verbose > 1)
    s = format (s, "    Name: ");

  /* Unwind execrated counted-label sheit */
  pos = *curpos;
  len = *pos++;

  while (len)
    {
      for (i = 0; i < len; i++)
	vec_add1 (s, *pos++);

      len = *pos++;
      if (len)
	vec_add1 (s, '.');
      else
	{
	  vec_add1 (s, ':');
	  vec_add1 (s, ' ');
	}
    }

  qp = (dns_query_t *) pos;
  if (verbose > 1)
    {
      switch (clib_net_to_host_u16 (qp->type))
	{
	case DNS_TYPE_A:
	  s = format (s, "type A\n");
	  break;
	case DNS_TYPE_AAAA:
	  s = format (s, "type AAAA\n");
	  break;
	case DNS_TYPE_ALL:
	  s = format (s, "type ALL\n");
	  break;

	default:
	  s = format (s, "type %d\n", clib_net_to_host_u16 (qp->type));
	  break;
	}
    }

  pos += sizeof (*qp);

  *curpos = pos;
  return s;
}

/**
 * format dns reply data
 * verbose > 1, dump everything
 * verbose == 1, dump all A and AAAA records
 * verbose == 0, dump one A record, and one AAAA record
 */

u8 *
format_dns_reply_data (u8 * s, va_list * args)
{
  u8 *reply = va_arg (*args, u8 *);
  u8 **curpos = va_arg (*args, u8 **);
  int verbose = va_arg (*args, int);
  int *print_ip4 = va_arg (*args, int *);
  int *print_ip6 = va_arg (*args, int *);
  int len;
  u8 *pos, *pos2;
  dns_rr_t *rr;
  int i;
  int initial_pointer_chase = 0;
  u16 *tp;
  u16 rrtype_host_byte_order;

  pos = pos2 = *curpos;

  if (verbose > 1)
    s = format (s, "    ");

  /* chase pointer? almost always yes here... */
  if (pos2[0] == 0xc0)
    {
      pos2 = reply + pos2[1];
      pos += 2;
      initial_pointer_chase = 1;
    }

  len = *pos2++;

  while (len)
    {
      for (i = 0; i < len; i++)
	{
	  if (verbose > 1)
	    vec_add1 (s, *pos2);
	  pos2++;
	}
      len = *pos2++;
      if (len)
	{
	  if (verbose > 1)
	    vec_add1 (s, '.');
	}
      else
	{
	  if (verbose > 1)
	    vec_add1 (s, ' ');
	}
    }

  if (initial_pointer_chase == 0)
    pos = pos2;

  rr = (dns_rr_t *) pos;
  rrtype_host_byte_order = clib_net_to_host_u16 (rr->type);

  switch (rrtype_host_byte_order)
    {
    case DNS_TYPE_A:
      if (verbose > 1)
	{
	  s = format (s, "A: ttl %d %U\n", clib_net_to_host_u32 (rr->ttl),
		      format_ip4_address, rr->rdata);
	}
      else
	{
	  if (*print_ip4)
	    s = format (s, "%U [%u] ", format_ip4_address, rr->rdata,
			clib_net_to_host_u32 (rr->ttl));
	  if (verbose == 0)
	    *print_ip4 = 0;

	}
      pos += sizeof (*rr) + 4;
      break;

    case DNS_TYPE_AAAA:
      if (verbose > 1)
	{
	  s = format (s, "AAAA: ttl %d %U\n", clib_net_to_host_u32 (rr->ttl),
		      format_ip6_address, rr->rdata);
	}
      else
	{
	  if (*print_ip6)
	    s = format (s, "%U [%u] ", format_ip6_address, rr->rdata,
			clib_net_to_host_u32 (rr->ttl));
	  if (verbose == 0)
	    *print_ip6 = 0;
	}
      pos += sizeof (*rr) + 16;
      break;

    case DNS_TYPE_TEXT:
      if (verbose > 1)
	{
	  s = format (s, "TEXT: ");
	  for (i = 0; i < clib_net_to_host_u16 (rr->rdlength); i++)
	    vec_add1 (s, rr->rdata[i]);
	  vec_add1 (s, '\n');
	}
      pos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
      break;

    case DNS_TYPE_HINFO:
      {
	/* Two counted strings. DGMS */
	u8 *len;
	u8 *curpos;
	int i;
	if (verbose > 1)
	  {
	    s = format (s, "HINFO: ");
	    len = rr->rdata;
	    curpos = len + 1;
	    for (i = 0; i < *len; i++)
	      vec_add1 (s, *curpos++);

	    vec_add1 (s, ' ');
	    len = curpos++;
	    for (i = 0; i < *len; i++)
	      vec_add1 (s, *curpos++);

	    vec_add1 (s, '\n');
	  }
      }
      pos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
      break;

    case DNS_TYPE_NAMESERVER:
      if (verbose > 1)
	{
	  s = format (s, "Nameserver: ");
	  pos2 = rr->rdata;

	  /* chase pointer? */
	  if (pos2[0] == 0xc0)
	    pos2 = reply + pos2[1];

	  len = *pos2++;

	  while (len)
	    {
	      for (i = 0; i < len; i++)
		vec_add1 (s, *pos2++);

	      /* chase pointer, typically to offset 12... */
	      if (pos2[0] == 0xC0)
		pos2 = reply + pos2[1];

	      len = *pos2++;
	      if (len)
		vec_add1 (s, '.');
	      else
		vec_add1 (s, '\n');
	    }
	}
      pos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
      break;

    case DNS_TYPE_MAIL_EXCHANGE:
      if (verbose > 1)
	{
	  tp = (u16 *) rr->rdata;

	  s = format (s, "Mail Exchange: Preference %d ", (u32)
		      clib_net_to_host_u16 (*tp));

	  pos2 = rr->rdata + 2;

	  /* chase pointer? */
	  if (pos2[0] == 0xc0)
	    pos2 = reply + pos2[1];

	  len = *pos2++;

	  while (len)
	    {
	      for (i = 0; i < len; i++)
		vec_add1 (s, *pos2++);

	      /* chase pointer */
	      if (pos2[0] == 0xC0)
		pos2 = reply + pos2[1];

	      len = *pos2++;
	      if (len)
		vec_add1 (s, '.');
	      else
		vec_add1 (s, '\n');
	    }
	}

      pos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
      break;

    case DNS_TYPE_PTR:
    case DNS_TYPE_CNAME:
      if (verbose > 1)
	{
	  tp = (u16 *) rr->rdata;

	  if (rrtype_host_byte_order == DNS_TYPE_CNAME)
	    s = format (s, "CNAME: ");
	  else
	    s = format (s, "PTR: ");

	  pos2 = rr->rdata;

	  /* chase pointer? */
	  if (pos2[0] == 0xc0)
	    pos2 = reply + pos2[1];

	  len = *pos2++;

	  while (len)
	    {
	      for (i = 0; i < len; i++)
		vec_add1 (s, *pos2++);

	      /* chase pointer */
	      if (pos2[0] == 0xC0)
		pos2 = reply + pos2[1];

	      len = *pos2++;
	      if (len)
		vec_add1 (s, '.');
	      else
		vec_add1 (s, '\n');
	    }
	}
      pos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
      break;

    default:
      if (verbose > 1)
	s = format (s, "type %d: len %d\n",
		    (int) clib_net_to_host_u16 (rr->type),
		    sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength));
      pos += sizeof (*rr) + clib_net_to_host_u16 (rr->rdlength);
      break;
    }

  *curpos = pos;

  return s;
}

u8 *
format_dns_reply (u8 * s, va_list * args)
{
  u8 *reply_as_u8 = va_arg (*args, u8 *);
  int verbose = va_arg (*args, int);
  dns_header_t *h;
  u16 id, flags;
  u8 *curpos;
  int i;
  int print_ip4 = 1;
  int print_ip6 = 1;

  h = (dns_header_t *) reply_as_u8;
  id = clib_net_to_host_u16 (h->id);
  flags = clib_net_to_host_u16 (h->flags);

  if (verbose > 1)
    {
      s = format (s, "DNS %s: id %d\n", (flags & DNS_QR) ? "reply" : "query",
		  id);
      s = format (s, "  %s %s %s %s\n",
		  (flags & DNS_RA) ? "recur" : "no-recur",
		  (flags & DNS_RD) ? "recur-des" : "no-recur-des",
		  (flags & DNS_TC) ? "trunc" : "no-trunc",
		  (flags & DNS_AA) ? "auth" : "non-auth");
      s = format (s, "  %d queries, %d answers, %d name-servers,"
		  " %d add'l recs\n",
		  clib_net_to_host_u16 (h->qdcount),
		  clib_net_to_host_u16 (h->anscount),
		  clib_net_to_host_u16 (h->nscount),
		  clib_net_to_host_u16 (h->arcount));
    }

  curpos = (u8 *) (h + 1);

  if (h->qdcount)
    {
      if (verbose > 1)
	s = format (s, "  Queries:\n");
      for (i = 0; i < clib_net_to_host_u16 (h->qdcount); i++)
	{
	  /* The query is variable-length, so curpos is a value-result parm */
	  s = format (s, "%U", format_dns_query, &curpos, verbose);
	}
    }
  if (h->anscount)
    {
      if (verbose > 1)
	s = format (s, "  Replies:\n");

      for (i = 0; i < clib_net_to_host_u16 (h->anscount); i++)
	{
	  /* curpos is a value-result parm */
	  s = format (s, "%U", format_dns_reply_data, reply_as_u8, &curpos,
		      verbose, &print_ip4, &print_ip6);
	}
    }
  return s;
}

u8 *
format_dns_cache (u8 * s, va_list * args)
{
  dns_main_t *dm = va_arg (*args, dns_main_t *);
  f64 now = va_arg (*args, f64);
  int verbose = va_arg (*args, int);
  u8 *name = va_arg (*args, u8 *);
  dns_cache_entry_t *ep;
  char *ss;
  uword *p;

  if (dm->is_enabled == 0)
    {
      s = format (s, "The DNS cache is disabled...");
      return s;
    }

  if (pool_elts (dm->entries) == 0)
    {
      s = format (s, "The DNS cache is empty...");
      return s;
    }

  dns_cache_lock (dm);

  if (name)
    {
      p = hash_get_mem (dm->cache_entry_by_name, name);
      if (!p)
	{
	  s = format (s, "%s is not in the cache...", name);
	  dns_cache_unlock (dm);
	  return (s);
	}

      ep = pool_elt_at_index (dm->entries, p[0]);
      /* Magic to spit out a C-initializer to research hemorrhoids... */
      if (verbose == 3)
	{
	  int i, j;
	  s = format (s, "static u8 dns_reply_data_initializer[] =\n");
	  s = format (s, "{\n");
	  j = 0;
	  for (i = 0; i < vec_len (ep->dns_response); i++)
	    {
	      if (j++ == 8)
		{
		  j = 0;
		  vec_add1 (s, '\n');
		}
	      s = format (s, "0x%02x, ", ep->dns_response[i]);
	    }
	  s = format (s, "};\n");
	}
      else
	{
	  if (ep->flags & DNS_CACHE_ENTRY_FLAG_VALID)
	    {
	      ASSERT (ep->dns_response);
	      if (ep->flags & DNS_CACHE_ENTRY_FLAG_STATIC)
		ss = "[S] ";
	      else
		ss = "    ";

	      if (verbose < 2 && ep->flags & DNS_CACHE_ENTRY_FLAG_CNAME)
		s = format (s, "%s%s -> %s", ss, ep->name, ep->cname);
	      else
		s = format (s, "%s%s -> %U", ss, ep->name,
			    format_dns_reply, ep->dns_response, verbose);
	      if (!(ep->flags & DNS_CACHE_ENTRY_FLAG_STATIC))
		{
		  f64 time_left = ep->expiration_time - now;
		  if (time_left > 0.0)
		    s = format (s, "  TTL left %.1f", time_left);
		  else
		    s = format (s, "  EXPIRED");
		}
	    }
	  else
	    {
	      ASSERT (ep->dns_request);
	      s = format (s, "[P] %U", format_dns_reply, ep->dns_request,
			  verbose);
	    }
	  vec_add1 (s, '\n');
	}
      return s;
    }

  /* *INDENT-OFF* */
  pool_foreach (ep, dm->entries,
  ({
    if (ep->flags & DNS_CACHE_ENTRY_FLAG_VALID)
      {
        ASSERT (ep->dns_response);
        if (ep->flags & DNS_CACHE_ENTRY_FLAG_STATIC)
          ss = "[S] ";
        else
          ss = "    ";

        if (verbose < 2 && ep->flags & DNS_CACHE_ENTRY_FLAG_CNAME)
          s = format (s, "%s%s -> %s", ss, ep->name, ep->cname);
        else
          s = format (s, "%s%s -> %U", ss, ep->name,
                      format_dns_reply,
                      ep->dns_response,
                      verbose);
        if (!(ep->flags & DNS_CACHE_ENTRY_FLAG_STATIC))
          {
            f64 time_left = ep->expiration_time - now;
            if (time_left > 0.0)
              s = format (s, "  TTL left %.1f", time_left);
            else
              s = format (s, "  EXPIRED");

            if (verbose > 2)
              s = format (s, "    %d client notifications pending\n",
                          vec_len(ep->pending_api_requests));
          }
      }
    else
      {
        ASSERT (ep->dns_request);
        s = format (s, "[P] %U", format_dns_reply, ep->dns_request,
                    verbose);
      }
    vec_add1 (s, '\n');
  }));
  /* *INDENT-ON* */

  dns_cache_unlock (dm);

  return s;
}

static clib_error_t *
show_dns_cache_command_fn (vlib_main_t * vm,
			   unformat_input_t * input, vlib_cli_command_t * cmd)
{
  dns_main_t *dm = &dns_main;
  int verbose = 0;
  u8 *name = 0;
  f64 now = vlib_time_now (vm);

  while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
    {
      if (unformat (input, "verbose %d", &verbose))
	;
      else if (unformat (input, "verbose"))
	verbose = 1;
      else if (unformat (input, "name %s", &name))
	;
      else
	return clib_error_return (0, "unknown input `%U'",
				  format_unformat_error, input);
    }

  vlib_cli_output (vm, "%U", format_dns_cache, dm, now, verbose, name);

  return 0;
}

/* *INDENT-OFF* */
VLIB_CLI_COMMAND (show_dns_cache_command) =
{
  .path = "show dns cache",
  .short_help = "show dns cache [verbose [nn]]",
  .function = show_dns_cache_command_fn,
};
/* *INDENT-ON* */

static clib_error_t *
dns_cache_add_del_command_fn (vlib_main_t * vm,
			      unformat_input_t * input,
			      vlib_cli_command_t * cmd)
{
  dns_main_t *dm = &dns_main;
  u8 *dns_reply_data;
  u8 *name;
  int is_add = -1;
  int is_clear = -1;
  int rv;
  clib_error_t *error;

  if (unformat (input, "add"))
    is_add = 1;
  if (unformat (input, "del"))
    is_add = 0;
  if (unformat (input, "clear"))
    is_clear = 1;

  if (is_add == -1 && is_clear == -1)
    return clib_error_return (0, "add / del / clear required...");

  if (is_clear == 1)
    {
      rv = dns_cache_clear (dm);
      switch (rv)
	{
	case 0:
	  return 0;

	case VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED:
	  error = clib_error_return (0, "Name resolution not enabled");
	  return error;
	}
    }

  /* Delete (by name)? */
  if (is_add == 0)
    {
      if (unformat (input, "%v", &name))
	{
	  rv = dns_delete_by_name (dm, name);
	  switch (rv)
	    {
	    case VNET_API_ERROR_NO_SUCH_ENTRY:
	      error = clib_error_return (0, "%v not in the cache...", name);
	      vec_free (name);
	      return error;

	    case VNET_API_ERROR_NAME_RESOLUTION_NOT_ENABLED:
	      error = clib_error_return (0, "Name resolution not enabled");
	      vec_free (name);
	      return error;

	    case 0:
	      vec_free (name);
	      return 0;

	    default:
	      error = clib_error_return (0, "dns_delete_by_name returned %d",
					 rv);
	      vec_free (name);
	      return error;
	    }
	}
      return clib_error_return (0, "unknown input `%U'",
				format_unformat_error, input);
    }

  /* Note: dns_add_static_entry consumes the name vector if OK... */
  if (unformat (input, "%U", unformat_dns_reply, &dns_reply_data, &name))
    {
      rv = dns_add_static_entry (dm, name, dns_reply_data);
      switch (rv)
	{
	case VNET_API_ERROR_ENTRY_ALREADY_EXISTS:
	  vec_free (name);
	  vec_free (dns_reply_data);
	  return clib_error_return (0, "%v already in the cache...", name);
	case 0:
	  return 0;

	default:
	  return clib_error_return (0, "dns_add_static_entry returned %d",
				    rv);
	}
    }

  return 0;
}

/* *INDENT-OFF* */
VLIB_CLI_COMMAND (dns_cache_add_del_command) =
{
  .path = "dns cache",
  .short_help = "dns cache [add|del|clear] <name> [ip4][ip6]",
  .function = dns_cache_add_del_command_fn,
};
/* *INDENT-ON* */

#define DNS_FORMAT_TEST 1

#if DNS_FORMAT_TEST > 0
#if 0
/* yahoo.com */
static u8 dns_reply_data_initializer[] =
  { 0x0, 0x0, 0x81, 0x80, 0x0, 0x1, 0x0, 0x10, 0x0, 0x0, 0x0, 0x0, 0x5,
  0x79, 0x61, 0x68, 0x6f, 0x6f, 0x3, 0x63, 0x6f, 0x6d,
  0x0,				/* null lbl */
  0x0, 0xff,			/* type ALL */
  0x0, 0x1,			/* class IN */
  0xc0, 0xc,			/* pointer to yahoo.com name */
  0x0, 0x10, 0x0, 0x1, 0x0, 0x0, 0x6, 0x5c, 0x0, 0x24, 0x23,
  0x76, 0x3d, 0x73, 0x70, 0x66, 0x31, 0x20, 0x72, 0x65, 0x64, 0x69, 0x72,
  0x65, 0x63, 0x74, 0x3d, 0x5f, 0x73, 0x70, 0x66, 0x2e, 0x6d, 0x61, 0x69,
  0x6c, 0x2e, 0x79, 0x61, 0x68, 0x6f, 0x6f, 0x2e, 0x63, 0x6f, 0x6d, 0xc0,
  0xc, 0x0, 0x2, 0x0, 0x1, 0x0, 0x1, 0x50, 0xd4, 0x0, 0x6, 0x3, 0x6e, 0x73,
  0x35, 0xc0, 0xc, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0, 0x1, 0x50, 0xd4, 0x0,
  0x6, 0x3, 0x6e, 0x73, 0x34, 0xc0, 0xc, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0,
  0x1, 0x50, 0xd4, 0x0, 0x6, 0x3, 0x6e, 0x73, 0x31, 0xc0, 0xc, 0xc0, 0xc,
  0x0, 0x2, 0x0, 0x1, 0x0, 0x1, 0x50, 0xd4, 0x0, 0x6, 0x3, 0x6e, 0x73, 0x32,
  0xc0, 0xc, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0, 0x1, 0x50, 0xd4, 0x0, 0x6,
  0x3, 0x6e, 0x73, 0x33, 0xc0, 0xc, 0xc0, 0xc, 0x0, 0xf, 0x0, 0x1, 0x0, 0x0,
  0x6, 0x5c, 0x0, 0x19, 0x0, 0x1, 0x4, 0x6d, 0x74, 0x61, 0x36, 0x3, 0x61,
  0x6d, 0x30, 0x8, 0x79, 0x61, 0x68, 0x6f, 0x6f, 0x64, 0x6e, 0x73, 0x3,
  0x6e,
  0x65, 0x74, 0x0, 0xc0, 0xc, 0x0, 0xf, 0x0, 0x1, 0x0, 0x0, 0x6, 0x5c, 0x0,
  0x9, 0x0, 0x1, 0x4, 0x6d, 0x74, 0x61, 0x37, 0xc0, 0xb8, 0xc0, 0xc, 0x0,
  0xf, 0x0, 0x1, 0x0, 0x0, 0x6, 0x5c, 0x0, 0x9, 0x0, 0x1, 0x4, 0x6d, 0x74,
  0x61, 0x35, 0xc0, 0xb8, 0xc0, 0xc, 0x0, 0x1c, 0x0, 0x1, 0x0, 0x0, 0x6,
  0x5c, 0x0, 0x10, 0x20, 0x1, 0x49, 0x98, 0x0, 0x44, 0x2, 0x4, 0x0, 0x0,
  0x0,
  0x0, 0x0, 0x0, 0x0, 0xa7, 0xc0, 0xc, 0x0, 0x1c, 0x0, 0x1, 0x0, 0x0, 0x6,
  0x5c, 0x0, 0x10, 0x20, 0x1, 0x49, 0x98, 0x0, 0xc, 0xa, 0x6, 0x0, 0x0, 0x0,
  0x0, 0x0, 0x2, 0x40, 0x8, 0xc0, 0xc, 0x0, 0x1c, 0x0, 0x1, 0x0, 0x0, 0x6,
  0x5c, 0x0, 0x10, 0x20, 0x1, 0x49, 0x98, 0x0, 0x58, 0xc, 0x2, 0x0, 0x0,
  0x0,
  0x0, 0x0, 0x0, 0x0, 0xa9, 0xc0, 0xc, 0x0, 0x1, 0x0, 0x1, 0x0, 0x0, 0x6,
  0x5c, 0x0, 0x4, 0x62, 0x8a, 0xfd, 0x6d, 0xc0, 0xc, 0x0, 0x1, 0x0, 0x1,
  0x0,
  0x0, 0x6, 0x5c, 0x0, 0x4, 0xce, 0xbe, 0x24, 0x2d, 0xc0, 0xc, 0x0, 0x1,
  0x0,
  0x1, 0x0, 0x0, 0x6, 0x5c, 0x0, 0x4, 0x62, 0x8b, 0xb4, 0x95, 0xc0, 0xc,
  0x0,
  0x6, 0x0, 0x1, 0x0, 0x0, 0x6, 0x5c, 0x0, 0x2d, 0xc0, 0x7b, 0xa, 0x68,
  0x6f,
  0x73, 0x74, 0x6d, 0x61, 0x73, 0x74, 0x65, 0x72, 0x9, 0x79, 0x61, 0x68,
  0x6f, 0x6f, 0x2d, 0x69, 0x6e, 0x63, 0xc0, 0x12, 0x78, 0x3a, 0x85, 0x44,
  0x0, 0x0, 0xe, 0x10, 0x0, 0x0, 0x1, 0x2c, 0x0, 0x1b, 0xaf, 0x80, 0x0, 0x0,
  0x2, 0x58
};

/* www.cisco.com, has no addresses in reply */
static u8 dns_reply_data_initializer[] = {
  0x00, 0x01, 0x81, 0x80, 0x00, 0x01, 0x00, 0x01,
  0x00, 0x00, 0x00, 0x00, 0x03, 0x77, 0x77, 0x77, 0x05,
  0x63, 0x69, 0x73, 0x63, 0x6f, 0x03, 0x63, 0x6f, 0x6d,

  0x00, 0x00, 0xff, 0x00, 0x01, 0xc0, 0x0c, 0x00, 0x05,
  0x00, 0x01, 0x00, 0x00, 0x0b, 0xd3, 0x00, 0x1a, 0x03,
  0x77, 0x77, 0x77, 0x05, 0x63, 0x69, 0x73, 0x63, 0x6f,
  0x03, 0x63, 0x6f, 0x6d, 0x06, 0x61, 0x6b, 0x61, 0x64,
  0x6e, 0x73, 0x03, 0x6e, 0x65, 0x74, 0x00,
};
#else
/* google.com */
static u8 dns_reply_data_initializer[] =
  { 0x0, 0x0, 0x81, 0x80, 0x0, 0x1, 0x0, 0xe, 0x0, 0x0, 0x0, 0x0, 0x6,
  0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x3, 0x63, 0x6f, 0x6d, 0x0, 0x0, 0xff,
  0x0, 0x1, 0xc0, 0xc, 0x0, 0x1, 0x0, 0x1, 0x0, 0x0, 0x1, 0x2b, 0x0, 0x4,
  0xac, 0xd9, 0x3, 0x2e, 0xc0, 0xc, 0x0, 0x1c, 0x0, 0x1, 0x0, 0x0, 0x1,
  0x2b,
  0x0, 0x10, 0x26, 0x7, 0xf8, 0xb0, 0x40, 0x4, 0x8, 0xf, 0x0, 0x0, 0x0, 0x0,
  0x0, 0x0, 0x20, 0xe, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0, 0x1, 0x51, 0x7f,
  0x0, 0x6, 0x3, 0x6e, 0x73, 0x31, 0xc0, 0xc, 0xc0, 0xc, 0x0, 0x6, 0x0, 0x1,
  0x0, 0x0, 0x0, 0x3b, 0x0, 0x22, 0xc0, 0x54, 0x9, 0x64, 0x6e, 0x73, 0x2d,
  0x61, 0x64, 0x6d, 0x69, 0x6e, 0xc0, 0xc, 0xa, 0x3d, 0xc7, 0x30, 0x0, 0x0,
  0x3, 0x84, 0x0, 0x0, 0x3, 0x84, 0x0, 0x0, 0x7, 0x8, 0x0, 0x0, 0x0, 0x3c,
  0xc0, 0xc, 0x0, 0xf, 0x0, 0x1, 0x0, 0x0, 0x2, 0x57, 0x0, 0x11, 0x0, 0x1e,
  0x4, 0x61, 0x6c, 0x74, 0x32, 0x5, 0x61, 0x73, 0x70, 0x6d, 0x78, 0x1, 0x6c,
  0xc0, 0xc, 0xc0, 0xc, 0x0, 0xf, 0x0, 0x1, 0x0, 0x0, 0x2, 0x57, 0x0, 0x4,
  0x0, 0xa, 0xc0, 0x9b, 0xc0, 0xc, 0x0, 0x10, 0x0, 0x1, 0x0, 0x0, 0xe, 0xf,
  0x0, 0x24, 0x23, 0x76, 0x3d, 0x73, 0x70, 0x66, 0x31, 0x20, 0x69, 0x6e,
  0x63, 0x6c, 0x75, 0x64, 0x65, 0x3a, 0x5f, 0x73, 0x70, 0x66, 0x2e, 0x67,
  0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x63, 0x6f, 0x6d, 0x20, 0x7e, 0x61,
  0x6c, 0x6c, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0, 0x1, 0x51, 0x7f, 0x0, 0x6,
  0x3, 0x6e, 0x73, 0x32, 0xc0, 0xc, 0xc0, 0xc, 0x1, 0x1, 0x0, 0x1, 0x0, 0x1,
  0x51, 0x7f, 0x0, 0xf, 0x0, 0x5, 0x69, 0x73, 0x73, 0x75, 0x65, 0x70, 0x6b,
  0x69, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0,
  0x1, 0x51, 0x7f, 0x0, 0x6, 0x3, 0x6e, 0x73, 0x34, 0xc0, 0xc, 0xc0, 0xc,
  0x0, 0xf, 0x0, 0x1, 0x0, 0x0, 0x2, 0x57, 0x0, 0x9, 0x0, 0x28, 0x4, 0x61,
  0x6c, 0x74, 0x33, 0xc0, 0x9b, 0xc0, 0xc, 0x0, 0x2, 0x0, 0x1, 0x0, 0x1,
  0x51, 0x7f, 0x0, 0x6, 0x3, 0x6e, 0x73, 0x33, 0xc0, 0xc, 0xc0, 0xc, 0x0,
  0xf, 0x0, 0x1, 0x0, 0x0, 0x2, 0x57, 0x0, 0x9, 0x0, 0x32, 0x4, 0x61, 0x6c,
  0x74, 0x34, 0xc0, 0x9b, 0xc0, 0xc, 0x0, 0xf, 0x0, 0x1, 0x0, 0x0, 0x2,
  0x57,
  0x0, 0x9, 0x0, 0x14, 0x4, 0x61, 0x6c, 0x74, 0x31, 0xc0, 0x9b
};
#endif

static clib_error_t *
test_dns_fmt_command_fn (vlib_main_t * vm,
			 unformat_input_t * input, vlib_cli_command_t * cmd)
{
  u8 *dns_reply_data = 0;
  int verbose = 0;
  int rv;
  vl_api_dns_resolve_name_reply_t _rm, *rmp = &_rm;

  while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
    {
      if (unformat (input, "verbose %d", &verbose))
	;
      else if (unformat (input, "verbose"))
	verbose = 1;
      else
	return clib_error_return (0, "unknown input `%U'",
				  format_unformat_error, input);
    }

  vec_validate (dns_reply_data, ARRAY_LEN (dns_reply_data_initializer) - 1);

  memcpy (dns_reply_data, dns_reply_data_initializer,
	  ARRAY_LEN (dns_reply_data_initializer));

  vlib_cli_output (vm, "%U", format_dns_reply, dns_reply_data, verbose);

  memset (rmp, 0, sizeof (*rmp));

  rv = vnet_dns_response_to_reply (dns_reply_data, rmp, 0 /* ttl-ptr */ );

  switch (rv)
    {
    case VNET_API_ERROR_NAME_SERVER_NO_ADDRESSES:
      vlib_cli_output (vm, "no addresses found...");
      break;

    default:
      vlib_cli_output (vm, "response to reply returned %d", rv);
      break;

    case 0:
      if (rmp->ip4_set)
	vlib_cli_output (vm, "ip4 address: %U", format_ip4_address,
			 (ip4_address_t *) rmp->ip4_address);
      if (rmp->ip6_set)
	vlib_cli_output (vm, "ip6 address: %U", format_ip6_address,
			 (ip6_address_t *) rmp->ip6_address);
      break;
    }

  vec_free (dns_reply_data);

  return 0;
}


/* *INDENT-OFF* */
VLIB_CLI_COMMAND (test_dns_fmt_command) =
{
  .path = "test dns format",
  .short_help = "test dns format",
  .function = test_dns_fmt_command_fn,
};
/* *INDENT-ON* */

static clib_error_t *
test_dns_unfmt_command_fn (vlib_main_t * vm,
			   unformat_input_t * input, vlib_cli_command_t * cmd)
{
  u8 *dns_reply_data = 0;
  int verbose = 0;
  int reply_set = 0;

  while (unformat_check_input (input) != UNFORMAT_END_OF_INPUT)
    {
      if (unformat (input, "verbose %d", &verbose))
	;
      else if (unformat (input, "verbose"))
	verbose = 1;
      else if (unformat (input, "%U", unformat_dns_reply, &dns_reply_data))
	reply_set = 1;
      else
	return clib_error_return (0, "unknown input `%U'",
				  format_unformat_error, input);
    }

  if (reply_set == 0)
    return clib_error_return (0, "dns data not set...");

  vlib_cli_output (vm, "%U", format_dns_reply, dns_reply_data, verbose);

  vec_free (dns_reply_data);

  return 0;
}

/* *INDENT-OFF* */
VLIB_CLI_COMMAND (test_dns_unfmt_command) =
{
  .path = "test dns unformat",
  .short_help = "test dns unformat <name> [ip4][ip6]",
  .function = test_dns_unfmt_command_fn,
};
/* *INDENT-ON* */

static clib_error_t *
test_dns_expire_command_fn (vlib_main_t * vm,
			    unformat_input_t * input,
			    vlib_cli_command_t * cmd)
{
  dns_main_t *dm = &dns_main;
  u8 *name;
  uword *p;
  clib_error_t *e;
  dns_cache_entry_t *ep;

  if (unformat (input, "%v", &name))
    {
      vec_add1 (name, 0);
      _vec_len (name) -= 1;
    }

  dns_cache_lock (dm);

  p = hash_get_mem (dm->cache_entry_by_name, name);
  if (!p)
    {
      dns_cache_unlock (dm);
      e = clib_error_return (0, "%s is not in the cache...", name);
      vec_free (name);
      return e;
    }

  ep = pool_elt_at_index (dm->entries, p[0]);

  ep->expiration_time = 0;

  return 0;
}

/* *INDENT-OFF* */
VLIB_CLI_COMMAND (test_dns_expire_command) =
{
  .path = "test dns expire",
  .short_help = "test dns expire <name>",
  .function = test_dns_expire_command_fn,
};
/* *INDENT-ON* */
#endif

/*
 * fd.io coding-style-patch-verification: ON
 *
 * Local Variables:
 * eval: (c-set-style "gnu")
 * End:
 */
