1
0
Fork 0
mirror of https://github.com/reactos/reactos.git synced 2025-05-30 06:28:34 +00:00

[DNSRSLVR] Add support for IP6 hosts file entries

This commit is contained in:
Eric Kohl 2019-12-01 17:17:50 +01:00
parent 962ff6e2fa
commit c35ebdfeb6

View file

@ -8,11 +8,14 @@
*/ */
#include "precomp.h" #include "precomp.h"
#include <inaddr.h>
#include <in6addr.h>
#define NDEBUG #define NDEBUG
#include <debug.h> #include <debug.h>
static WCHAR szHexChar[] = L"0123456789abcdef";
static static
PWSTR PWSTR
@ -50,104 +53,51 @@ AnsiToUnicode(
static static
BOOL BOOL
ParseV4Address( ParseIpv4Address(
LPCSTR AddressString, _In_ PCSTR AddressString,
OUT PDWORD pAddress) _Out_ PIN_ADDR pAddress)
{ {
CHAR *cp; PCSTR pTerminator = NULL;
DWORD val, base; NTSTATUS Status;
unsigned char c;
DWORD parts[4], *pp = parts;
cp = (CHAR *)AddressString; Status = RtlIpv4StringToAddressA(AddressString,
TRUE,
&pTerminator,
pAddress);
if (NT_SUCCESS(Status) && pTerminator != NULL && *pTerminator == '\0')
return TRUE;
if (!AddressString) return FALSE;
return FALSE; }
if (!isdigit(*cp))
return FALSE;
again: static
/* BOOL
* Collect number up to ``.''. ParseIpv6Address(
* Values are specified as for C: _In_ LPCSTR AddressString,
* 0x=hex, 0=octal, other=decimal. _Out_ PIN6_ADDR pAddress)
*/ {
val = 0; base = 10; PCSTR pTerminator = NULL;
if (*cp == '0') NTSTATUS Status;
{
if (*++cp == 'x' || *cp == 'X')
base = 16, cp++;
else
base = 8;
}
while ((c = *cp)) Status = RtlIpv6StringToAddressA(AddressString,
{ &pTerminator,
if (isdigit(c)) pAddress);
{ if (NT_SUCCESS(Status) && pTerminator != NULL && *pTerminator == '\0')
val = (val * base) + (c - '0'); return TRUE;
cp++;
continue;
}
if (base == 16 && isxdigit(c)) return FALSE;
{
val = (val << 4) + (c + 10 - (islower(c) ? 'a' : 'A'));
cp++;
continue;
}
break;
}
if (*cp == '.')
{
/*
* Internet format:
* a.b.c.d
*/
if (pp >= parts + 4)
return FALSE;
*pp++ = val;
cp++;
goto again;
}
/* Check for trailing characters */
if (*cp && *cp > ' ')
return FALSE;
if (pp >= parts + 4)
return FALSE;
*pp++ = val;
/*
* Concoct the address according to
* the number of parts specified.
*/
if ((DWORD)(pp - parts) != 4)
return FALSE;
if (parts[0] > 0xff || parts[1] > 0xff || parts[2] > 0xff || parts[3] > 0xff)
return FALSE;
val = (parts[3] << 24) | (parts[2] << 16) | (parts[1] << 8) | parts[0];
if (pAddress)
*pAddress = val;
return TRUE;
} }
static static
VOID VOID
AddV4HostEntries( AddIpv4HostEntries(
PWSTR pszHostName, PWSTR pszHostName,
DWORD dwIpAddress) PIN_ADDR pAddress)
{ {
DNS_RECORDW ARecord, PtrRecord; DNS_RECORDW ARecord, PtrRecord;
WCHAR szInAddrArpaName[32]; WCHAR szReverseName[32];
/* Prepare the A record */ /* Prepare the A record */
ZeroMemory(&ARecord, sizeof(DNS_RECORDW)); ZeroMemory(&ARecord, sizeof(DNS_RECORDW));
@ -157,19 +107,19 @@ AddV4HostEntries(
ARecord.wDataLength = sizeof(DNS_A_DATA); ARecord.wDataLength = sizeof(DNS_A_DATA);
ARecord.dwTtl = 86400; ARecord.dwTtl = 86400;
ARecord.Data.A.IpAddress = dwIpAddress; ARecord.Data.A.IpAddress = pAddress->S_un.S_addr;
swprintf(szInAddrArpaName,
L"%u.%u.%u.%u.in-addr.arpa",
(dwIpAddress >> 24) & 0xFF,
(dwIpAddress >> 16) & 0xFF,
(dwIpAddress >> 8) & 0xFF,
dwIpAddress & 0xFF);
/* Prepare the PTR record */ /* Prepare the PTR record */
swprintf(szReverseName,
L"%u.%u.%u.%u.in-addr.arpa",
pAddress->S_un.S_un_b.s_b4,
pAddress->S_un.S_un_b.s_b3,
pAddress->S_un.S_un_b.s_b2,
pAddress->S_un.S_un_b.s_b1);
ZeroMemory(&PtrRecord, sizeof(DNS_RECORDW)); ZeroMemory(&PtrRecord, sizeof(DNS_RECORDW));
PtrRecord.pName = szInAddrArpaName; PtrRecord.pName = szReverseName;
PtrRecord.wType = DNS_TYPE_PTR; PtrRecord.wType = DNS_TYPE_PTR;
PtrRecord.wDataLength = sizeof(DNS_PTR_DATA); PtrRecord.wDataLength = sizeof(DNS_PTR_DATA);
PtrRecord.dwTtl = 86400; PtrRecord.dwTtl = 86400;
@ -181,6 +131,56 @@ AddV4HostEntries(
} }
static
VOID
AddIpv6HostEntries(
PWSTR pszHostName,
PIN6_ADDR pAddress)
{
DNS_RECORDW AAAARecord, PtrRecord;
WCHAR szReverseName[80];
DWORD i, j, k;
/* Prepare the AAAA record */
ZeroMemory(&AAAARecord, sizeof(DNS_RECORDW));
AAAARecord.pName = pszHostName;
AAAARecord.wType = DNS_TYPE_AAAA;
AAAARecord.wDataLength = sizeof(DNS_AAAA_DATA);
AAAARecord.dwTtl = 86400;
CopyMemory(&AAAARecord.Data.AAAA.Ip6Address,
&pAddress->u.Byte,
sizeof(IN6_ADDR));
/* Prepare the PTR record */
ZeroMemory(szReverseName, sizeof(szReverseName));
for (i = 0; i < sizeof(IN6_ADDR); i++)
{
j = 4 * i;
k = sizeof(IN6_ADDR) - 1 - i;
szReverseName[j] = szHexChar[pAddress->u.Byte[k] & 0xF];
szReverseName[j + 1] = L'.';
szReverseName[j + 2] = szHexChar[(pAddress->u.Byte[k] >> 4) & 0xF];
szReverseName[j + 3] = L'.';
}
wcscat(szReverseName, L"ip6.arpa");
ZeroMemory(&PtrRecord, sizeof(DNS_RECORDW));
PtrRecord.pName = szReverseName;
PtrRecord.wType = DNS_TYPE_PTR;
PtrRecord.wDataLength = sizeof(DNS_PTR_DATA);
PtrRecord.dwTtl = 86400;
PtrRecord.Data.PTR.pNameHost = pszHostName;
DnsIntCacheAddEntry(&AAAARecord);
DnsIntCacheAddEntry(&PtrRecord);
}
static static
FILE * FILE *
OpenHostsFile(VOID) OpenHostsFile(VOID)
@ -285,7 +285,8 @@ ReadHostsFile(VOID)
CHAR szLineBuffer[512]; CHAR szLineBuffer[512];
FILE *pHostFile = NULL; FILE *pHostFile = NULL;
CHAR *Ptr, *NameStart, *NameEnd, *AddressStart, *AddressEnd; CHAR *Ptr, *NameStart, *NameEnd, *AddressStart, *AddressEnd;
DWORD Address; struct in_addr Ipv4Address;
struct in6_addr Ipv6Address;
PWSTR pszHostName; PWSTR pszHostName;
pHostFile = OpenHostsFile(); pHostFile = OpenHostsFile();
@ -374,15 +375,25 @@ ReadHostsFile(VOID)
DPRINT("%s ==> %s\n", NameStart, AddressStart); DPRINT("%s ==> %s\n", NameStart, AddressStart);
if (ParseV4Address(AddressStart, &Address)) if (ParseIpv4Address(AddressStart, &Ipv4Address))
{ {
DPRINT("IP4: %s ==> 0x%08lx\n", AddressStart, Address); DPRINT("IPv4: %s\n", AddressStart);
pszHostName = AnsiToUnicode(NameStart); pszHostName = AnsiToUnicode(NameStart);
if (pszHostName != NULL) if (pszHostName != NULL)
{ {
AddV4HostEntries(pszHostName, Address); AddIpv4HostEntries(pszHostName, &Ipv4Address);
HeapFree(GetProcessHeap(), 0, pszHostName);
}
}
else if (ParseIpv6Address(AddressStart, &Ipv6Address))
{
DPRINT("IPv6: %s\n", AddressStart);
pszHostName = AnsiToUnicode(NameStart);
if (pszHostName != NULL)
{
AddIpv6HostEntries(pszHostName, &Ipv6Address);
HeapFree(GetProcessHeap(), 0, pszHostName); HeapFree(GetProcessHeap(), 0, pszHostName);
} }
} }