/** @file
  Copyright (c) 2010 - 2014, Intel Corporation. All rights reserved.<BR>
  This program and the accompanying materials are licensed and made available
  under the terms and conditions of the BSD License which accompanies this
  distribution.  The full text of the license may be found at
  http://opensource.org/licenses/bsd-license.php.

  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
**/
/*  $NetBSD: getnameinfo.c,v 1.45 2006/10/15 16:14:46 christos Exp $  */
/*  $KAME: getnameinfo.c,v 1.45 2000/09/25 22:43:56 itojun Exp $  */

/*
 * Copyright (c) 2000 Ben Harris.
 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 * 3. Neither the name of the project nor the names of its contributors
 *    may be used to endorse or promote products derived from this software
 *    without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 * SUCH DAMAGE.
 */

/*
 * Issues to be discussed:
 * - Thread safe-ness must be checked
 * - RFC2553 says that we should raise error on short buffer.  X/Open says
 *   we need to truncate the result.  We obey RFC2553 (and X/Open should be
 *   modified).  ipngwg rough consensus seems to follow RFC2553.
 * - What is "local" in NI_FQDN?
 * - NI_NAMEREQD and NI_NUMERICHOST conflict with each other.
 * - (KAME extension) always attach textual scopeid (fe80::1%lo0), if
 *   sin6_scope_id is filled - standardization status?
 *   XXX breaks backward compat for code that expects no scopeid.
 *   beware on merge.
 */

#define INET6   1

#include <sys/cdefs.h>
#if defined(LIBC_SCCS) && !defined(lint)
__RCSID("$NetBSD: getnameinfo.c,v 1.45 2006/10/15 16:14:46 christos Exp $");
#endif /* LIBC_SCCS and not lint */

#include "namespace.h"
#include <sys/types.h>
#include <sys/socket.h>
#include <net/if.h>
#include <net/if_dl.h>
//#include <net/if_ieee1394.h>
//#include <net/if_types.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <arpa/nameser.h>
#include <assert.h>
#include <limits.h>
#include <netdb.h>
#include <resolv.h>
#include <stddef.h>
#include <string.h>

#include <net/servent.h>

#define CLLADDR(x)          ( LLADDR(x) )
#define endservent_r(svd)   endservent()
#define getservbyport_r(Port,pProto,pSv,pSvd)   getservbyport(Port,pProto)

#ifdef __weak_alias
__weak_alias(getnameinfo,_getnameinfo)
#endif

static
int
hexname(
  const u_int8_t * cp,
  size_t len,
  char * host,
  socklen_t hostlen
  );

static const struct afd {
  int   a_af;
  socklen_t a_addrlen;
  socklen_t a_socklen;
  int   a_off;
} afdl [] = {
#ifdef INET6
  {PF_INET6, sizeof(struct in6_addr), sizeof(struct sockaddr_in6),
    offsetof(struct sockaddr_in6, sin6_addr)},
#endif
  {PF_INET, sizeof(struct in_addr), sizeof(struct sockaddr_in),
    offsetof(struct sockaddr_in, sin_addr)},
  {0, 0, 0, 0},
};

struct sockinet {
  u_char  si_len;
  u_char  si_family;
  u_short si_port;
};

static int getnameinfo_inet __P((const struct sockaddr *, socklen_t, char *,
    socklen_t, char *, socklen_t, int));
#ifdef INET6
static int ip6_parsenumeric __P((const struct sockaddr *, const char *, char *,
         socklen_t, int));
static int ip6_sa2str __P((const struct sockaddr_in6 *, char *, size_t,
         int));
#endif
static int getnameinfo_link __P((const struct sockaddr *, socklen_t, char *,
    socklen_t, char *, socklen_t, int));
static int hexname __P((const u_int8_t *, size_t, char *, socklen_t));

/*
 * Top-level getnameinfo() code.  Look at the address family, and pick an
 * appropriate function to call.
 */
int
getnameinfo(
  const struct sockaddr * sa,
  socklen_t salen,
  char * host,
  socklen_t hostlen,
  char * serv,
  socklen_t servlen,
  int flags
  )
{

  switch (sa->sa_family) {
  case AF_INET:
  case AF_INET6:
    return getnameinfo_inet(sa, salen, host, hostlen,
        serv, servlen, flags);
  case AF_LINK:
    return getnameinfo_link(sa, salen, host, hostlen,
        serv, servlen, flags);
  default:
    return EAI_FAMILY;
  }
}


/*
 * getnameinfo_inet():
 * Format an IPv4 or IPv6 sockaddr into a printable string.
 */
static
int
getnameinfo_inet(
  const struct sockaddr * sa,
  socklen_t salen,
  char * host,
  socklen_t hostlen,
  char * serv,
  socklen_t servlen,
  int flags
  )
{
  const struct afd *afd;
  struct servent *sp;
  struct hostent *hp;
  u_short port;
  int family, i;
  const char *addr;
  u_int32_t v4a;
  char numserv[512];
  char numaddr[512];

  /* sa is checked below */
  /* host may be NULL */
  /* serv may be NULL */

  if (sa == NULL)
    return EAI_FAIL;

#ifdef BSD4_4
  if (sa->sa_len != salen)
    return EAI_FAIL;
#endif

  family = sa->sa_family;
  for (i = 0; afdl[i].a_af; i++)
    if (afdl[i].a_af == family) {
      afd = &afdl[i];
      goto found;
    }
  return EAI_FAMILY;

 found:
  if (salen != afd->a_socklen)
    return EAI_FAIL;

  /* network byte order */
  port = ((const struct sockinet *)(const void *)sa)->si_port;
  addr = (const char *)(const void *)sa + afd->a_off;

  if (serv == NULL || servlen == 0) {
    /*
     * do nothing in this case.
     * in case you are wondering if "&&" is more correct than
     * "||" here: rfc2553bis-03 says that serv == NULL OR
     * servlen == 0 means that the caller does not want the result.
     */
  } else {
    if (flags & NI_NUMERICSERV)
      sp = NULL;
    else {
      struct servent_data svd;
//      struct servent sv;

      (void)memset(&svd, 0, sizeof(svd));
      sp = getservbyport_r(port,
        (flags & NI_DGRAM) ? "udp" : "tcp", &sv, &svd);
      endservent_r(&svd);
    }
    if (sp) {
      if (strlen(sp->s_name) + 1 > servlen)
        return EAI_MEMORY;
      strlcpy(serv, sp->s_name, servlen);
    } else {
      snprintf(numserv, sizeof(numserv), "%u", ntohs(port));
      if (strlen(numserv) + 1 > servlen)
        return EAI_MEMORY;
      strlcpy(serv, numserv, servlen);
    }
  }

  switch (sa->sa_family) {
  case AF_INET:
    v4a = (u_int32_t)
        ntohl(((const struct sockaddr_in *)
        (const void *)sa)->sin_addr.s_addr);
    if (IN_MULTICAST(v4a) || IN_EXPERIMENTAL(v4a))
      flags |= NI_NUMERICHOST;
    v4a >>= IN_CLASSA_NSHIFT;
    if (v4a == 0)
      flags |= NI_NUMERICHOST;
    break;
#ifdef INET6
  case AF_INET6:
      {
    const struct sockaddr_in6 *sin6;
    sin6 = (const struct sockaddr_in6 *)(const void *)sa;
    switch (sin6->sin6_addr.s6_addr[0]) {
    case 0x00:
      if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr))
        ;
      else if (IN6_IS_ADDR_LOOPBACK(&sin6->sin6_addr))
        ;
      else
        flags |= NI_NUMERICHOST;
      break;
    default:
      if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) {
        flags |= NI_NUMERICHOST;
      }
      else if (IN6_IS_ADDR_MULTICAST(&sin6->sin6_addr))
        flags |= NI_NUMERICHOST;
      break;
    }
      }
    break;
#endif
  }
  if (host == NULL || hostlen == 0) {
    /*
     * do nothing in this case.
     * in case you are wondering if "&&" is more correct than
     * "||" here: rfc2553bis-03 says that host == NULL or
     * hostlen == 0 means that the caller does not want the result.
     */
  } else if (flags & NI_NUMERICHOST) {
    size_t numaddrlen;

    /* NUMERICHOST and NAMEREQD conflicts with each other */
    if (flags & NI_NAMEREQD)
      return EAI_NONAME;

    switch(afd->a_af) {
#ifdef INET6
    case AF_INET6:
    {
      int error;

      if ((error = ip6_parsenumeric(sa, addr, host,
                  hostlen, flags)) != 0)
        return(error);
      break;
    }
#endif
    default:
      if (inet_ntop(afd->a_af, addr, numaddr, sizeof(numaddr))
          == NULL)
        return EAI_SYSTEM;
      numaddrlen = strlen(numaddr);
      if (numaddrlen + 1 > hostlen) /* don't forget terminator */
        return EAI_MEMORY;
      strlcpy(host, numaddr, hostlen);
      break;
    }
  } else {
    hp = gethostbyaddr(addr, afd->a_addrlen, afd->a_af);

    if (hp) {
#if 0
      /*
       * commented out, since "for local host" is not
       * implemented here - see RFC2553 p30
       */
      if (flags & NI_NOFQDN) {
        char *p;
        p = strchr(hp->h_name, '.');
        if (p)
          *p = '\0';
      }
#endif
      if (strlen(hp->h_name) + 1 > hostlen) {
        return EAI_MEMORY;
      }
      strlcpy(host, hp->h_name, hostlen);
    } else {
      if (flags & NI_NAMEREQD)
        return EAI_NONAME;
      switch(afd->a_af) {
#ifdef INET6
      case AF_INET6:
      {
        int error;

        if ((error = ip6_parsenumeric(sa, addr, host,
                    hostlen,
                    flags)) != 0)
          return(error);
        break;
      }
#endif
      default:
        if (inet_ntop(afd->a_af, addr, host,
            hostlen) == NULL)
          return EAI_SYSTEM;
        break;
      }
    }
  }
  return(0);
}

#ifdef INET6
static int
ip6_parsenumeric(
  const struct sockaddr *sa,
  const char *addr,
  char *host,
  socklen_t hostlen,
  int flags
  )
{
  size_t numaddrlen;
  char numaddr[512];

  _DIAGASSERT(sa != NULL);
  _DIAGASSERT(addr != NULL);
  _DIAGASSERT(host != NULL);

  if (inet_ntop(AF_INET6, addr, numaddr, sizeof(numaddr)) == NULL)
    return EAI_SYSTEM;

  numaddrlen = strlen(numaddr);
  if (numaddrlen + 1 > hostlen) /* don't forget terminator */
    return EAI_OVERFLOW;
  strlcpy(host, numaddr, hostlen);

  if (((const struct sockaddr_in6 *)(const void *)sa)->sin6_scope_id) {
    char zonebuf[MAXHOSTNAMELEN];
    int zonelen;

    zonelen = ip6_sa2str(
        (const struct sockaddr_in6 *)(const void *)sa,
        zonebuf, sizeof(zonebuf), flags);
    if (zonelen < 0)
      return EAI_OVERFLOW;
    if ((size_t) zonelen + 1 + numaddrlen + 1 > hostlen)
      return EAI_OVERFLOW;
    /* construct <numeric-addr><delim><zoneid> */
    memcpy(host + numaddrlen + 1, zonebuf,
        (size_t)zonelen);
    host[numaddrlen] = SCOPE_DELIMITER;
    host[numaddrlen + 1 + zonelen] = '\0';
  }

  return 0;
}

/* ARGSUSED */
static int
ip6_sa2str(
  const struct sockaddr_in6 *sa6,
  char *buf,
  size_t bufsiz,
  int flags
  )
{
#if 0
  unsigned int ifindex;
  const struct in6_addr *a6;
#endif
  int n;

  _DIAGASSERT(sa6 != NULL);
  _DIAGASSERT(buf != NULL);

#if 0
  ifindex = (unsigned int)sa6->sin6_scope_id;
  a6 = &sa6->sin6_addr;
#endif

#ifdef NI_NUMERICSCOPE
  if ((flags & NI_NUMERICSCOPE) != 0) {
    n = snprintf(buf, bufsiz, "%u", sa6->sin6_scope_id);
    if ((n < 0) || ((size_t)n >= bufsiz))
      return -1;
    else
      return n;
  }
#endif

#if 0
  /* if_indextoname() does not take buffer size.  not a good api... */
  if ((IN6_IS_ADDR_LINKLOCAL(a6) || IN6_IS_ADDR_MC_LINKLOCAL(a6)) &&
      bufsiz >= IF_NAMESIZE) {
    char *p = if_indextoname(ifindex, buf);
    if (p) {
      return(strlen(p));
    }
  }
#endif  //  0

  /* last resort */
  n = snprintf(buf, bufsiz, "%u", sa6->sin6_scope_id);
  if (n < 0 || (size_t) n >= bufsiz)
    return -1;
  else
    return n;
}
#endif /* INET6 */


/*
 * getnameinfo_link():
 * Format a link-layer address into a printable format, paying attention to
 * the interface type.
 */
/* ARGSUSED */
static
int
getnameinfo_link (
  const struct sockaddr * sa,
  socklen_t salen,
  char * host,
  socklen_t hostlen,
  char * serv,
  socklen_t servlen,
  int flags
  )
{
  const struct sockaddr_dl *sdl =
      (const struct sockaddr_dl *)(const void *)sa;
//  const struct ieee1394_hwaddr *iha;
  int n;

  if (serv != NULL && servlen > 0)
    *serv = '\0';

  if (sdl->sdl_nlen == 0 && sdl->sdl_alen == 0 && sdl->sdl_slen == 0) {
    n = snprintf(host, hostlen, "link#%u", sdl->sdl_index);
    if (n < 0 || (socklen_t) n > hostlen) {
      *host = '\0';
      return EAI_MEMORY;
    }
    return 0;
  }

#if 0
  switch (sdl->sdl_type) {
#ifdef IFT_ECONET
  case IFT_ECONET:
    if (sdl->sdl_alen < 2)
      return EAI_FAMILY;
    if (CLLADDR(sdl)[1] == 0)
      n = snprintf(host, hostlen, "%u", CLLADDR(sdl)[0]);
    else
      n = snprintf(host, hostlen, "%u.%u",
          CLLADDR(sdl)[1], CLLADDR(sdl)[0]);
    if (n < 0 || (socklen_t) n >= hostlen) {
      *host = '\0';
      return EAI_MEMORY;
    } else
      return 0;
#endif
  case IFT_IEEE1394:
    if (sdl->sdl_alen < sizeof(iha->iha_uid))
      return EAI_FAMILY;
    iha =
        (const struct ieee1394_hwaddr *)(const void *)CLLADDR(sdl);
    return hexname(iha->iha_uid, sizeof(iha->iha_uid),
        host, hostlen);
  /*
   * The following have zero-length addresses.
   * IFT_ATM  (net/if_atmsubr.c)
   * IFT_FAITH  (net/if_faith.c)
   * IFT_GIF  (net/if_gif.c)
   * IFT_LOOP (net/if_loop.c)
   * IFT_PPP  (net/if_ppp.c, net/if_spppsubr.c)
   * IFT_SLIP (net/if_sl.c, net/if_strip.c)
   * IFT_STF  (net/if_stf.c)
   * IFT_L2VLAN (net/if_vlan.c)
   * IFT_PROPVIRTUAL (net/if_bridge.h>
   */
  /*
   * The following use IPv4 addresses as link-layer addresses:
   * IFT_OTHER  (net/if_gre.c)
   */
  case IFT_ARCNET: /* default below is believed correct for all these. */
  case IFT_ETHER:
  case IFT_FDDI:
  case IFT_HIPPI:
  case IFT_ISO88025:
  default:
#endif  //  0
    return hexname((const u_int8_t *)CLLADDR(sdl),
        (size_t)sdl->sdl_alen, host, hostlen);
//  }
}

static
int
hexname(
  const u_int8_t * cp,
  size_t len,
  char * host,
  socklen_t hostlen
  )
{
  int n;
  size_t i;
  char *outp = host;

  *outp = '\0';
  for (i = 0; i < len; i++) {
    n = snprintf(outp, hostlen, "%s%02x",
        i ? ":" : "", cp[i]);
    if (n < 0 || (socklen_t) n >= hostlen) {
      *host = '\0';
      return EAI_MEMORY;
    }
    outp += n;
    hostlen -= n;
  }
  return 0;
}
