Index: trunk/src/VBox/Devices/Network/DrvNAT.cpp
===================================================================
--- trunk/src/VBox/Devices/Network/DrvNAT.cpp	(revision 39599)
+++ trunk/src/VBox/Devices/Network/DrvNAT.cpp	(revision 39766)
@@ -1009,4 +1009,26 @@
 }
 
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+static int drvNATConstructDNSMappings(unsigned iInstance, PDRVNAT pThis, PCFGMNODE pMappingsCfg)
+{
+    int rc = VINF_SUCCESS;
+    LogFlowFunc(("ENTER: iInstance:%d\n", iInstance));
+    for (PCFGMNODE pNode = CFGMR3GetFirstChild(pMappingsCfg); pNode; pNode = CFGMR3GetNextChild(pNode))
+    {
+        if (!CFGMR3AreValuesValid(pNode, "HostName\0HostIP\0"))
+            return PDMDRV_SET_ERROR(pThis->pDrvIns, VERR_PDM_DRVINS_UNKNOWN_CFG_VALUES,
+                                    N_("Unknown configuration in dns mapping"));
+        char szHostName[255];
+        RT_ZERO(szHostName);
+        GET_STRING(rc, pThis, pNode, "HostName", szHostName[0], sizeof(szHostName));
+        struct in_addr HostIP;
+        GETIP_DEF(rc, pThis, pNode, HostIP, INADDR_ANY);
+        slirp_add_host_resolver_mapping(pThis->pNATState, szHostName, HostIP.s_addr);
+    }
+    LogFlowFunc(("LEAVE: %Rrc\n", rc));
+    return rc;
+}
+#endif /* !VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER */
+
 
 /**
@@ -1026,4 +1048,11 @@
     for (PCFGMNODE pNode = CFGMR3GetFirstChild(pCfg); pNode; pNode = CFGMR3GetNextChild(pNode))
     {
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+        char szNodeName[32];
+        CFGMR3GetName(pNode, szNodeName, 32);
+        if (   !RTStrICmp(szNodeName, "HostResolverMappings")
+            || !RTStrICmp(szNodeName, "AttachedDriver"))
+            continue;
+#endif
         /*
          * Validate the port forwarding config.
@@ -1159,5 +1188,9 @@
                               "SockRcv\0SockSnd\0TcpRcv\0TcpSnd\0"
                               "ICMPCacheLimit\0"
-                              "SoMaxConnection\0"))
+                              "SoMaxConnection\0"
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+                              "HostResolverMappings\0"
+#endif
+                            ))
         return PDMDRV_SET_ERROR(pDrvIns, VERR_PDM_DRVINS_UNKNOWN_CFG_VALUES,
                                 N_("Unknown NAT configuration option, only supports PassDomain,"
@@ -1293,4 +1326,13 @@
 #endif
 
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+        PCFGMNODE pMappingsCfg = CFGMR3GetChild(pCfg, "HostResolverMappings");
+
+        if (pMappingsCfg)
+        {
+            rc = drvNATConstructDNSMappings(pDrvIns->iInstance, pThis, pMappingsCfg);
+            AssertRC(rc);
+        }
+#endif
         rc = drvNATConstructRedir(pDrvIns->iInstance, pThis, pCfg, Network);
         if (RT_SUCCESS(rc))
Index: trunk/src/VBox/Devices/Network/slirp/libalias/alias_dns.c
===================================================================
--- trunk/src/VBox/Devices/Network/slirp/libalias/alias_dns.c	(revision 39599)
+++ trunk/src/VBox/Devices/Network/slirp/libalias/alias_dns.c	(revision 39766)
@@ -68,14 +68,17 @@
 
 /* see RFC 1035(4.1) */
-static int dns_alias_handler(PNATState pData, int type);
+static int  dns_alias_handler(PNATState pData, int type);
 static void CStr2QStr(const char *pcszStr, char *pszQStr, size_t cQStr);
 static void QStr2CStr(const char *pcszQStr, char *pszStr, size_t cStr);
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+static void alterHostentWithDataFromDNSMap(PNATState pData, struct hostent *pHostent);
+#endif
 
 static int
-fingerprint(struct libalias *la, struct ip *pip, struct alias_data *ah)
+fingerprint(struct libalias *la, struct ip *pIp, struct alias_data *ah)
 {
 
     NOREF(la);
-    NOREF(pip);
+    NOREF(pIp);
     if (!ah->dport || !ah->sport || !ah->lnk)
         return -1;
@@ -93,14 +96,14 @@
 }
 
-static void doanswer(union dnsmsg_header *hdr, struct dns_meta_data *pReqMeta, char *qname, struct ip *pip, struct hostent *h)
+static void doanswer(union dnsmsg_header *pHdr, struct dns_meta_data *pReqMeta, char *pszQname, struct ip *pIp, struct hostent *pHostent)
 {
     int i;
 
-    if (!h)
-    {
-        hdr->X.qr = 1; /* response */
-        hdr->X.aa = 1;
-        hdr->X.rd = 1;
-        hdr->X.rcode = 3;
+    if (!pHostent)
+    {
+        pHdr->X.qr = 1; /* response */
+        pHdr->X.aa = 1;
+        pHdr->X.rd = 1;
+        pHdr->X.rcode = 3;
     }
     else
@@ -117,15 +120,15 @@
 #if 0
         /* here is no compressed names+answers + new query */
-        m_inc(m, h->h_length * sizeof(struct dnsmsg_answer) + strlen(qname) + 2 * sizeof(uint16_t));
+        m_inc(m, pHostent->h_length * sizeof(struct dnsmsg_answer) + strlen(pszQname) + 2 * sizeof(uint16_t));
 #endif
-        packet_len = (pip->ip_hl << 2)
+        packet_len = (pIp->ip_hl << 2)
                    + sizeof(struct udphdr)
                    + sizeof(union dnsmsg_header)
-                   + strlen(qname)
+                   + strlen(pszQname)
                    + sizeof(struct dns_meta_data); /* ip + udp + header + query */
-        query = (char *)&hdr[1];
-
-        strcpy(query, qname);
-        query += strlen(qname) + 1;
+        query = (char *)&pHdr[1];
+
+        strcpy(query, pszQname);
+        query += strlen(pszQname) + 1;
         /* class & type informations lay right after symbolic inforamtion. */
         meta = (struct dns_meta_data *)query;
@@ -136,9 +139,9 @@
         answers = (char *)&meta[1];
 
-        off = (char *)&hdr[1] - (char *)hdr;
+        off = (char *)&pHdr[1] - (char *)pHdr;
         off |= (0x3 << 14);
 
         /* add aliases */
-        for (cstr = h->h_aliases; *cstr; cstr++)
+        for (cstr = pHostent->h_aliases; *cstr; cstr++)
         {
             uint16_t len;
@@ -148,10 +151,10 @@
             ans->meta.class = htons(1);
             *(uint32_t *)ans->ttl = htonl(3600); /* 1h */
-            c = (addr_off == (uint16_t)~0 ? h->h_name : *cstr);
+            c = (addr_off == (uint16_t)~0 ? pHostent->h_name : *cstr);
             len = strlen(c) + 2;
             ans->rdata_len = htons(len);
             ans->rdata[len - 1] = 0;
             CStr2QStr(c, (char *)ans->rdata, len);
-            off = (char *)&ans->rdata - (char *)hdr;
+            off = (char *)&ans->rdata - (char *)pHdr;
             off |= (0x3 << 14);
             if (addr_off == (uint16_t)~0)
@@ -159,9 +162,9 @@
             answers = (char *)&ans[1] + len - 2;  /* note: 1 symbol already counted */
             packet_len += sizeof(struct dnsmsg_answer) + len - 2;
-            hdr->X.ancount++;
+            pHdr->X.ancount++;
         }
         /* add addresses */
 
-        for(i = 0; i < h->h_length && h->h_addr_list[i] != NULL; ++i)
+        for(i = 0; i < pHostent->h_length && pHostent->h_addr_list[i] != NULL; ++i)
         {
             struct dnsmsg_answer *ans = (struct dnsmsg_answer *)answers;
@@ -172,45 +175,45 @@
             *(uint32_t *)ans->ttl = htonl(3600); /* 1h */
             ans->rdata_len = htons(4); /* IPv4 */
-            *(uint32_t *)ans->rdata = *(uint32_t *)h->h_addr_list[i];
+            *(uint32_t *)ans->rdata = *(uint32_t *)pHostent->h_addr_list[i];
             answers = (char *)&ans[1] + 2;
             packet_len += sizeof(struct dnsmsg_answer) + 3;
-            hdr->X.ancount++;
-        }
-        hdr->X.qr = 1; /* response */
-        hdr->X.aa = 1;
-        hdr->X.rd = 1;
-        hdr->X.ra = 1;
-        hdr->X.rcode = 0;
-        HTONS(hdr->X.ancount);
+            pHdr->X.ancount++;
+        }
+        pHdr->X.qr = 1; /* response */
+        pHdr->X.aa = 1;
+        pHdr->X.rd = 1;
+        pHdr->X.ra = 1;
+        pHdr->X.rcode = 0;
+        HTONS(pHdr->X.ancount);
         /* don't forget update m_len */
-        pip->ip_len = htons(packet_len);
+        pIp->ip_len = htons(packet_len);
     }
 }
 
 static int
-protohandler(struct libalias *la, struct ip *pip, struct alias_data *ah)
+protohandler(struct libalias *la, struct ip *pIp, struct alias_data *ah)
 {
     int i;
     /* Parse dns request */
     char *qw_qname = NULL;
-    struct hostent *h = NULL;
-    char cname[255];
+    struct hostent *pHostent = NULL;
+    char pszCname[255];
     int cname_len = 0;
     struct dns_meta_data *meta;
 
     struct udphdr *udp = NULL;
-    union dnsmsg_header *hdr = NULL;
+    union dnsmsg_header *pHdr = NULL;
     NOREF(la);
     NOREF(ah);
-    udp = (struct udphdr *)ip_next(pip);
-    hdr = (union dnsmsg_header *)udp_next(udp);
-
-    if (hdr->X.qr == 1)
+    udp = (struct udphdr *)ip_next(pIp);
+    pHdr = (union dnsmsg_header *)udp_next(udp);
+
+    if (pHdr->X.qr == 1)
         return 0; /* this is respose */
 
-    memset(cname, 0, sizeof(cname));
-    qw_qname = (char *)&hdr[1];
-    Assert((ntohs(hdr->X.qdcount) == 1));
-    if ((ntohs(hdr->X.qdcount) != 1))
+    memset(pszCname, 0, sizeof(pszCname));
+    qw_qname = (char *)&pHdr[1];
+    Assert((ntohs(pHdr->X.qdcount) == 1));
+    if ((ntohs(pHdr->X.qdcount) != 1))
     {
         static bool fMultiWarn;
@@ -223,12 +226,12 @@
     }
 
-    for (i = 0; i < ntohs(hdr->X.qdcount); ++i)
+    for (i = 0; i < ntohs(pHdr->X.qdcount); ++i)
     {
         meta = (struct dns_meta_data *)(qw_qname + strlen(qw_qname) + 1);
-        Log(("qname:%s qtype:%hd qclass:%hd\n",
+        Log(("pszQname:%s qtype:%hd qclass:%hd\n",
             qw_qname, ntohs(meta->type), ntohs(meta->class)));
 
-        QStr2CStr(qw_qname, cname, sizeof(cname));
-        cname_len = RTStrNLen(cname, sizeof(cname));
+        QStr2CStr(qw_qname, pszCname, sizeof(pszCname));
+        cname_len = RTStrNLen(pszCname, sizeof(pszCname));
         /* Some guests like win-xp adds _dot_ after host name
          * and after domain name (not passed with host resolver)
@@ -236,13 +239,18 @@
          */
         if (   cname_len > 2
-            && cname[cname_len - 1] == '.'
-            && cname[cname_len - 2] == '.')
-        {
-            cname[cname_len - 1] = 0;
-            cname[cname_len - 2] = 0;
-        }
-        h = gethostbyname(cname);
-        fprintf(stderr, "cname:%s\n", cname);
-        doanswer(hdr, meta, qw_qname, pip, h);
+            && pszCname[cname_len - 1] == '.'
+            && pszCname[cname_len - 2] == '.')
+        {
+            pszCname[cname_len - 1] = 0;
+            pszCname[cname_len - 2] = 0;
+        }
+        pHostent = gethostbyname(pszCname);
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+        if (   pHostent
+            && !LIST_EMPTY(&la->pData->DNSMapHead))
+            alterHostentWithDataFromDNSMap(la->pData, pHostent);
+#endif
+        fprintf(stderr, "pszCname:%s\n", pszCname);
+        doanswer(pHdr, meta, qw_qname, pIp, pHostent);
     }
 
@@ -252,7 +260,7 @@
      */
     udp->uh_sum = 0;
-    udp->uh_ulen = ntohs(htons(pip->ip_len) - (pip->ip_hl << 2));
-    pip->ip_sum = 0;
-    pip->ip_sum = LibAliasInternetChecksum(la, (uint16_t *)pip, pip->ip_hl << 2);
+    udp->uh_ulen = ntohs(htons(pIp->ip_len) - (pIp->ip_hl << 2));
+    pIp->ip_sum = 0;
+    pIp->ip_sum = LibAliasInternetChecksum(la, (uint16_t *)pIp, pIp->ip_hl << 2);
     return 0;
 }
@@ -367,2 +375,57 @@
     return error;
 }
+
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+static void alterHostentWithDataFromDNSMap(PNATState pData, struct hostent *pHostent)
+{
+    PDNSMAPPINGENTRY pDNSMapingEntry = NULL;
+    bool fMatch = false;
+    LIST_FOREACH(pDNSMapingEntry, &pData->DNSMapHead, MapList)
+    {
+        char **pszAlias = NULL;
+        if (!strcmp(pDNSMapingEntry->pszCName, pHostent->h_name))
+        {
+            fMatch = true;
+            break;
+        }
+
+        for (pszAlias = pHostent->h_aliases; *pszAlias && !fMatch; pszAlias++)
+        {
+            if (!strcmp(pDNSMapingEntry->pszCName, *pszAlias))
+            {
+
+                PDNSMAPPINGENTRY pDnsMapping = RTMemAllocZ(sizeof(DNSMAPPINGENTRY));
+                fMatch = true;
+                if (!pDnsMapping)
+                {
+                    LogFunc(("Can't allocate DNSMAPPINGENTRY\n"));
+                    LogFlowFuncLeave();
+                    return;
+                }
+                pDnsMapping->u32IpAddress = pDNSMapingEntry->u32IpAddress;
+                pDnsMapping->pszCName = RTStrDup(pHostent->h_name);
+                if (!pDnsMapping->pszCName)
+                {
+                    LogFunc(("Can't allocate enough room for %s\n", pHostent->h_name));
+                    RTMemFree(pDnsMapping);
+                    LogFlowFuncLeave();
+                    return;
+                }
+                LIST_INSERT_HEAD(&pData->DNSMapHead, pDnsMapping, MapList);
+            }
+        }
+        if (fMatch)
+            break;
+    }
+
+    /* h_lenght is lenght of h_addr_list in bytes, so we check that we have enough space for IPv4 address */
+    if (   fMatch
+        && pHostent->h_length >= sizeof(uint32_t)
+        && pDNSMapingEntry)
+    {
+        pHostent->h_length = 1;
+        *(uint32_t *)pHostent->h_addr_list[0] = pDNSMapingEntry->u32IpAddress;
+    }
+
+}
+#endif
Index: trunk/src/VBox/Devices/Network/slirp/libslirp.h
===================================================================
--- trunk/src/VBox/Devices/Network/slirp/libslirp.h	(revision 39599)
+++ trunk/src/VBox/Devices/Network/slirp/libslirp.h	(revision 39766)
@@ -148,4 +148,8 @@
 # endif
 
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+void  slirp_add_host_resolver_mapping(PNATState pData, const char *pszHostName, uint32_t u32HostIP);
+#endif
+
 #ifdef __cplusplus
 }
Index: trunk/src/VBox/Devices/Network/slirp/slirp.c
===================================================================
--- trunk/src/VBox/Devices/Network/slirp/slirp.c	(revision 39599)
+++ trunk/src/VBox/Devices/Network/slirp/slirp.c	(revision 39766)
@@ -799,5 +799,16 @@
     nbt_alias_unload(pData);
     if (pData->fUseHostResolver)
+    {
         dns_alias_unload(pData);
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+        while (!LIST_EMPTY(&pData->DNSMapHead))
+        {
+            PDNSMAPPINGENTRY pDnsEntry = LIST_FIRST(&pData->DNSMapHead);
+            LIST_REMOVE(pDnsEntry, MapList);
+            RTStrFree(pDnsEntry->pszCName);
+            RTMemFree(pDnsEntry);
+        }
+#endif
+    }
     while (!LIST_EMPTY(&instancehead))
     {
@@ -2147,4 +2158,33 @@
     LogFlowFuncLeave();
 }
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+void  slirp_add_host_resolver_mapping(PNATState pData, const char *pszHostName, uint32_t u32HostIP)
+{
+    LogFlowFunc(("ENTER: pszHostName:%s, u32HostIP:%RTnaipv4\n", pszHostName, u32HostIP));
+    if (   pszHostName
+        || u32HostIP != INADDR_ANY
+        || u32HostIP != INADDR_BROADCAST)
+    {
+        PDNSMAPPINGENTRY pDnsMapping = RTMemAllocZ(sizeof(DNSMAPPINGENTRY));
+        if (!pDnsMapping)
+        {
+            LogFunc(("Can't allocate DNSMAPPINGENTRY\n"));
+            LogFlowFuncLeave();
+            return;
+        }
+        pDnsMapping->u32IpAddress = u32HostIP;
+        pDnsMapping->pszCName = RTStrDup(pszHostName);
+        if (!pDnsMapping->pszCName)
+        {
+            LogFunc(("Can't allocate enough room for %s\n", pszHostName));
+            RTMemFree(pDnsMapping);
+            LogFlowFuncLeave();
+            return;
+        }
+        LIST_INSERT_HEAD(&pData->DNSMapHead, pDnsMapping, MapList);
+    }
+    LogFlowFuncLeave();
+}
+#endif
 
 /* updates the arp cache
Index: trunk/src/VBox/Devices/Network/slirp/slirp_state.h
===================================================================
--- trunk/src/VBox/Devices/Network/slirp/slirp_state.h	(revision 39599)
+++ trunk/src/VBox/Devices/Network/slirp/slirp_state.h	(revision 39766)
@@ -65,4 +65,14 @@
 };
 LIST_HEAD(dns_domain_list_head, dns_domain_entry);
+
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+typedef struct DNSMAPPINGENTRY
+{
+    char        *pszCName;
+    uint32_t    u32IpAddress;
+    LIST_ENTRY(DNSMAPPINGENTRY) MapList;
+} DNSMAPPINGENTRY, *PDNSMAPPINGENTRY;
+typedef LIST_HEAD(DNSMAPPINGLISTHEAD, DNSMAPPINGENTRY) DNSMAPPINGLISTHEAD;
+#endif
 
 struct dns_entry
@@ -298,4 +308,7 @@
     int cInHomeAddressSize;
 #endif
+#ifdef VBOX_WITH_DNSMAPPING_IN_HOSTRESOLVER
+    DNSMAPPINGLISTHEAD DNSMapHead;
+#endif
 } NATState;
 
