ReactOS 0.4.16-dev-1638-g46c2a3c
address.c
Go to the documentation of this file.
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS system libraries
4 * FILE: dll/win32/iphlpapi/address.c
5 * PURPOSE: iphlpapi implementation - Adapter Address APIs
6 * PROGRAMMERS: Jérôme Gardou (jerome.gardou@reactos.org)
7 */
8
9#include "iphlpapi_private.h"
10
12#ifdef GetAdaptersAddressesV2
13/* Helper for GetAdaptersAddresses:
14 * Retrieves the list of network adapters from tcpip.sys */
15static
17GetInterfacesList(
18 _In_ HANDLE TcpFile,
20 _Out_ ULONG* InterfaceCount)
21{
22
24 IO_STATUS_BLOCK StatusBlock;
27
28 ZeroMemory(&TcpQueryInfo, sizeof(TcpQueryInfo));
29 TcpQueryInfo.ID.toi_class = INFO_CLASS_GENERIC;
30 TcpQueryInfo.ID.toi_type = INFO_TYPE_PROVIDER;
31 TcpQueryInfo.ID.toi_id = ENTITY_LIST_ID;
33 TcpQueryInfo.ID.toi_entity.tei_instance = 0;
34
36 TcpFile,
37 NULL,
38 NULL,
39 NULL,
40 &StatusBlock,
42 &TcpQueryInfo,
43 sizeof(TcpQueryInfo),
44 NULL,
45 0);
47 {
48 /* So we have to wait a bit */
50 if (NT_SUCCESS(Status))
51 Status = StatusBlock.Status;
52 }
53
54 if (!NT_SUCCESS(Status))
55 return Status;
56
57 BufferSize = StatusBlock.Information;
59 if (!*EntityList)
60 return STATUS_NO_MEMORY;
61
62 /* Do the real call */
64 TcpFile,
65 NULL,
66 NULL,
67 NULL,
68 &StatusBlock,
70 &TcpQueryInfo,
71 sizeof(TcpQueryInfo),
75 {
76 /* So we have to wait a bit */
78 if (NT_SUCCESS(Status))
79 Status = StatusBlock.Status;
80 }
81
82 if (!NT_SUCCESS(Status))
83 {
85 return Status;
86 }
87
88 *InterfaceCount = BufferSize / sizeof(TDIEntityID);
89 return Status;
90}
91
92static
94GetSnmpInfo(
95 _In_ HANDLE TcpFile,
96 _In_ TDIEntityID InterfaceID,
98{
100 IO_STATUS_BLOCK StatusBlock;
102
103 ZeroMemory(&TcpQueryInfo, sizeof(TcpQueryInfo));
104 TcpQueryInfo.ID.toi_class = INFO_CLASS_PROTOCOL;
105 TcpQueryInfo.ID.toi_type = INFO_TYPE_PROVIDER;
106 TcpQueryInfo.ID.toi_id = IP_MIB_STATS_ID;
107 TcpQueryInfo.ID.toi_entity = InterfaceID;
108
110 TcpFile,
111 NULL,
112 NULL,
113 NULL,
114 &StatusBlock,
116 &TcpQueryInfo,
117 sizeof(TcpQueryInfo),
118 Info,
119 sizeof(*Info));
120 if (Status == STATUS_PENDING)
121 {
122 /* So we have to wait a bit */
124 if (NT_SUCCESS(Status))
125 Status = StatusBlock.Status;
126 }
127
128 return Status;
129}
130
131static
133GetAddrEntries(
134 _In_ HANDLE TcpFile,
135 _In_ TDIEntityID InterfaceID,
137 _In_ ULONG NumEntries)
138{
140 IO_STATUS_BLOCK StatusBlock;
142
143 ZeroMemory(&TcpQueryInfo, sizeof(TcpQueryInfo));
144 TcpQueryInfo.ID.toi_class = INFO_CLASS_PROTOCOL;
145 TcpQueryInfo.ID.toi_type = INFO_TYPE_PROVIDER;
146 TcpQueryInfo.ID.toi_id = IP_MIB_ADDRTABLE_ENTRY_ID;
147 TcpQueryInfo.ID.toi_entity = InterfaceID;
148
150 TcpFile,
151 NULL,
152 NULL,
153 NULL,
154 &StatusBlock,
156 &TcpQueryInfo,
157 sizeof(TcpQueryInfo),
158 Entries,
159 NumEntries * sizeof(Entries[0]));
160 if (Status == STATUS_PENDING)
161 {
162 /* So we have to wait a bit */
164 if (NT_SUCCESS(Status))
165 Status = StatusBlock.Status;
166 }
167
168 return Status;
169}
170
171/*
172 * Fills the IFEntry buffer from tcpip.sys.
173 * The buffer size MUST be FIELD_OFFSET(IFEntry, if_descr[MAX_ADAPTER_DESCRIPTION_LENGTH + 1]).
174 * See MSDN IFEntry struct definition if you don't believe me. ;-)
175 */
176static
178GetInterfaceEntry(
179 _In_ HANDLE TcpFile,
180 _In_ TDIEntityID InterfaceID,
182{
184 IO_STATUS_BLOCK StatusBlock;
186
187 ZeroMemory(&TcpQueryInfo, sizeof(TcpQueryInfo));
188 TcpQueryInfo.ID.toi_class = INFO_CLASS_PROTOCOL;
189 TcpQueryInfo.ID.toi_type = INFO_TYPE_PROVIDER;
190 TcpQueryInfo.ID.toi_id = IP_MIB_STATS_ID;
191 TcpQueryInfo.ID.toi_entity = InterfaceID;
192
194 TcpFile,
195 NULL,
196 NULL,
197 NULL,
198 &StatusBlock,
200 &TcpQueryInfo,
201 sizeof(TcpQueryInfo),
202 Entry,
204 if (Status == STATUS_PENDING)
205 {
206 /* So we have to wait a bit */
208 if (NT_SUCCESS(Status))
209 Status = StatusBlock.Status;
210 }
211
212 return Status;
213}
214
215/* Helpers to get the list of DNS for an interface */
216static
217VOID
218EnumerateServerNameSize(
220 _In_ PWCHAR NameServer,
222{
224
225 /* This is just sizing here */
227 UNREFERENCED_PARAMETER(NameServer);
228
229 *BufferSize += sizeof(IP_ADAPTER_DNS_SERVER_ADDRESS) + sizeof(SOCKADDR);
230}
231
232static
233VOID
234EnumerateServerName(
236 _In_ PWCHAR NameServer,
238{
239 PIP_ADAPTER_DNS_SERVER_ADDRESS** Ptr = Data;
240 PIP_ADAPTER_DNS_SERVER_ADDRESS ServerAddress = **Ptr;
241
243
244 ServerAddress->Length = sizeof(IP_ADAPTER_DNS_SERVER_ADDRESS);
245 ServerAddress->Address.lpSockaddr = (PVOID)(ServerAddress + 1);
246 ServerAddress->Address.iSockaddrLength = sizeof(SOCKADDR);
247
248
249 /* Get the address from the server name string */
250 //FIXME: Only ipv4 for now...
252 NameServer,
253 AF_INET,
254 NULL,
255 ServerAddress->Address.lpSockaddr,
256 &ServerAddress->Address.iSockaddrLength))
257 {
258 /* Pass along, name conversion failed */
259 ERR("%S is not a valid IP address\n", NameServer);
260 return;
261 }
262
263 /* Go to next item */
264 ServerAddress->Next = (PVOID)(ServerAddress->Address.lpSockaddr + 1);
265 *Ptr = &ServerAddress->Next;
266}
267
268static
269VOID
270QueryFlags(
272 _In_ DWORD InterfaceLength,
274{
275 HKEY InterfaceKey;
276 CHAR KeyName[256];
278
279 *Flags = 0;
280
281 snprintf(KeyName, 256,
282 "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\%*s",
283 InterfaceLength, Interface);
284
286 {
287 Size = sizeof(DWORD);
288 if (RegQueryValueExA(InterfaceKey, "EnableDHCP", NULL, &Type, (LPBYTE)&Data, &Size) == ERROR_SUCCESS &&
289 Type == REG_DWORD && Data == 1)
290 {
291 *Flags |= IP_ADAPTER_DHCP_ENABLED;
292 }
293
294 Size = sizeof(DWORD);
295 if (RegQueryValueExA(InterfaceKey, "RegisterAdapterName", NULL, &Type, (LPBYTE)&Data, &Size) == ERROR_SUCCESS &&
296 Type == REG_DWORD && Data == 1)
297 {
298 *Flags |= IP_ADAPTER_REGISTER_ADAPTER_SUFFIX;
299 }
300
301 Size = 0;
302 if (RegQueryValueExA(InterfaceKey, "NameServer", NULL, &Type, (LPBYTE)&Data, &Size) != ERROR_SUCCESS)
303 {
304 *Flags |= IP_ADAPTER_DDNS_ENABLED;
305 }
306
307 RegCloseKey(InterfaceKey);
308 }
309
310 // FIXME: handle 0x8 -> 0x20
311}
312
313DWORD
314WINAPI
316GetAdaptersAddresses(
320 _Inout_ PIP_ADAPTER_ADDRESSES pAdapterAddresses,
321 _Inout_ PULONG pOutBufLen)
322{
324 HANDLE TcpFile;
325 TDIEntityID* InterfacesList;
326 ULONG InterfacesCount;
327 ULONG AdaptersCount = 0;
328 ULONG i;
329 ULONG TotalSize = 0, RemainingSize;
330 BYTE* Ptr = (BYTE*)pAdapterAddresses;
331 DWORD MIN_SIZE = 15 * 1024;
332 PIP_ADAPTER_ADDRESSES PreviousAA = NULL;
333
334 TRACE("Family %u, Flags 0x%08x, Reserved %p, pAdapterAddress %p, pOutBufLen %p\n",
335 Family, Flags, Reserved, pAdapterAddresses, pOutBufLen);
336
337 if (!pOutBufLen)
339
340 // FIXME: the exact needed size should be computed first, BEFORE doing any write to the output buffer.
341 // As suggested by MSDN, require a 15 KB buffer, which allows to React properly to length checks.
342 if(!Ptr || *pOutBufLen < MIN_SIZE)
343 {
344 *pOutBufLen = MIN_SIZE;
346 }
347
348 switch(Family)
349 {
350 case AF_INET:
351 break;
352 case AF_INET6:
353 /* One day maybe... */
354 FIXME("IPv6 is not supported in ReactOS!\n");
355 /* We got nothing to say in this case */
356 return ERROR_NO_DATA;
357 break;
358 case AF_UNSPEC:
359 WARN("IPv6 addresses ignored, IPv4 only\n");
360 Family = AF_INET;
361 break;
362 default:
363 ERR("Invalid family 0x%x\n", Family);
365 break;
366 }
367
368 RemainingSize = *pOutBufLen;
369 if (Ptr)
370 ZeroMemory(Ptr, RemainingSize);
371
372 /* open the tcpip driver */
373 Status = openTcpFile(&TcpFile, FILE_READ_DATA);
374 if (!NT_SUCCESS(Status))
375 {
376 ERR("Could not open handle to tcpip.sys. Status %08x\n", Status);
378 }
379
380 /* Get the interfaces list */
381 Status = GetInterfacesList(TcpFile, &InterfacesList, &InterfacesCount);
382 if (!NT_SUCCESS(Status))
383 {
384 ERR("Could not get adapters list. Status %08x\n", Status);
385 NtClose(TcpFile);
387 }
388
389 /* Let's see if we got any adapter. */
390 for (i = 0; i < InterfacesCount; i++)
391 {
393 ULONG CurrentAASize = 0;
394 ULONG FriendlySize = 0, DescriptionSize = 0;
395 ULONG DhcpDomainSize = 0, DomainSize = 0;
396
397 if (InterfacesList[i].tei_entity == IF_ENTITY)
398 {
399 BYTE EntryBuffer[FIELD_OFFSET(IFEntry, if_descr) +
401 IFEntry* Entry = (IFEntry*)EntryBuffer;
402
403 /* Remember we got one */
404 AdaptersCount++;
405
406 /* Set the pointer to this instance in the previous one*/
407 if(PreviousAA)
408 PreviousAA->Next = CurrentAA;
409
410 /* Of course we need some space for the base structure. */
411 CurrentAASize = sizeof(IP_ADAPTER_ADDRESSES);
412
413 /* Get the entry */
414 Status = GetInterfaceEntry(TcpFile, InterfacesList[i], Entry);
415 if (!NT_SUCCESS(Status))
416 goto Error;
417
418 TRACE("Got entity %*s, index %u.\n",
419 Entry->if_descrlen, &Entry->if_descr[0], Entry->if_index);
420
421 /* Add the adapter name */
422 CurrentAASize += Entry->if_descrlen + sizeof(CHAR);
423
424 /* Add the DNS suffix */
425 if (Entry->if_type != IF_TYPE_SOFTWARE_LOOPBACK)
426 {
427 HKEY InterfaceKey;
428 CHAR KeyName[256];
429 DWORD ValueType, ValueSize, Data;
430
431 snprintf(KeyName, 256,
432 "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\%*s",
433 Entry->if_descrlen, &Entry->if_descr[0]);
434
436 {
437 ValueSize = sizeof(DWORD);
438 if (RegQueryValueExW(InterfaceKey, L"EnableDHCP", NULL, &ValueType, (LPBYTE)&Data, &ValueSize) == ERROR_SUCCESS &&
439 ValueType == REG_DWORD && Data == 1)
440 {
441 ValueSize = sizeof(DWORD);
442 if (RegQueryValueExW(InterfaceKey, L"DhcpDomain", NULL, &ValueType, NULL, &ValueSize) == ERROR_SUCCESS &&
443 ValueType == REG_SZ)
444 {
445 /* We remove the null char, it will be re-added after */
446 DhcpDomainSize = ValueSize - sizeof(WCHAR);
447 CurrentAASize += DhcpDomainSize;
448 }
449 }
450 else
451 {
452 ValueSize = sizeof(DWORD);
453 if (RegQueryValueExW(InterfaceKey, L"Domain", NULL, &ValueType, NULL, &ValueSize) == ERROR_SUCCESS &&
454 ValueType == REG_SZ)
455 {
456 /* We remove the null char, it will be re-added after */
457 DomainSize = ValueSize - sizeof(WCHAR);
458 CurrentAASize += DomainSize;
459 }
460 }
461
462 RegCloseKey(InterfaceKey);
463 }
464 }
465
466 CurrentAASize += sizeof(WCHAR);
467
468 /* Add the description. */
469 if (Entry->if_type == IF_TYPE_SOFTWARE_LOOPBACK)
470 {
471 DescriptionSize = mbstowcs(NULL, (PCSTR)&Entry->if_descr[0], Entry->if_descrlen) * sizeof(WCHAR);
472 CurrentAASize += DescriptionSize;
473 }
474 else
475 {
476 HKEY ConnectionKey;
477 CHAR KeyName[256];
478 CHAR InstanceID[128];
479 DWORD ValueType = 0;
480 DWORD ValueSize = 0;
481
482 snprintf(KeyName, 256,
483 "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\%*s\\Connection",
484 Entry->if_descrlen, &Entry->if_descr[0]);
485
487 {
488 ValueSize = 128;
489 RegQueryValueExA(ConnectionKey, "PnpInstanceID", NULL, &ValueType, (LPBYTE)InstanceID, &ValueSize);
490 RegCloseKey(ConnectionKey);
491 }
492
493 if (ValueSize != 0)
494 {
495 sprintf(KeyName, "SYSTEM\\CurrentControlSet\\Enum\\%s", InstanceID);
496
498 {
499 ValueSize = 0;
500 if (RegQueryValueExW(ConnectionKey, L"DeviceDesc", NULL, &ValueType, NULL, &ValueSize) == ERROR_SUCCESS &&
501 ValueType == REG_SZ)
502 {
503 /* We remove the null char, it will be re-added after */
504 DescriptionSize = ValueSize - sizeof(WCHAR);
505 CurrentAASize += DescriptionSize;
506 }
507
508 RegCloseKey(ConnectionKey);
509 }
510 }
511 }
512
513 /* We always make sure to have enough room for empty string */
514 CurrentAASize += sizeof(WCHAR);
515
517 {
518 if (Entry->if_type == IF_TYPE_SOFTWARE_LOOPBACK)
519 {
520 FriendlySize = mbstowcs(NULL, (PCSTR)&Entry->if_descr[0], Entry->if_descrlen) * sizeof(WCHAR);
521 CurrentAASize += FriendlySize;
522 }
523 else
524 {
525 /* Get the friendly name */
526 HKEY ConnectionKey;
527 CHAR KeyName[256];
528
529 snprintf(KeyName, 256,
530 "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\%*s\\Connection",
531 Entry->if_descrlen, &Entry->if_descr[0]);
532
534 {
536 DWORD ValueSize = 0;
537
538 if (RegQueryValueExW(ConnectionKey, L"Name", NULL, &ValueType, NULL, &ValueSize) == ERROR_SUCCESS &&
539 ValueType == REG_SZ)
540 {
541 /* We remove the null char, it will be re-added after */
542 FriendlySize = ValueSize - sizeof(WCHAR);
543 CurrentAASize += FriendlySize;
544 }
545
546 RegCloseKey(ConnectionKey);
547 }
548 }
549
550 /* We always make sure to have enough room for empty string */
551 CurrentAASize += sizeof(WCHAR);
552 }
553
554 if (!(Flags & GAA_FLAG_SKIP_DNS_SERVER))
555 {
556 /* Enumerate the name servers */
557 HKEY InterfaceKey;
558 CHAR KeyName[256];
559
560 snprintf(KeyName, 256,
561 "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\%*s",
562 Entry->if_descrlen, &Entry->if_descr[0]);
563
565 {
566 EnumNameServers(InterfaceKey, NULL, &CurrentAASize, EnumerateServerNameSize);
567 RegCloseKey(InterfaceKey);
568 }
569 }
570
571 /* This is part of what we will need */
572 TotalSize += CurrentAASize;
573
574 /* Fill in the data */
575 if ((CurrentAA) && (RemainingSize >= CurrentAASize))
576 {
577 CurrentAA->Length = sizeof(IP_ADAPTER_ADDRESSES);
578 CurrentAA->IfIndex = Entry->if_index;
579 CopyMemory(CurrentAA->PhysicalAddress, Entry->if_physaddr, Entry->if_physaddrlen);
580 CurrentAA->PhysicalAddressLength = Entry->if_physaddrlen;
581 QueryFlags(&Entry->if_descr[0], Entry->if_descrlen, &CurrentAA->Flags);
582 CurrentAA->Mtu = Entry->if_mtu;
583 CurrentAA->IfType = Entry->if_type;
584 if(Entry->if_operstatus >= IF_OPER_STATUS_CONNECTING)
585 CurrentAA->OperStatus = IfOperStatusUp;
586 else
587 CurrentAA->OperStatus = IfOperStatusDown;
588
589 /* Next items */
590 Ptr = (BYTE*)(CurrentAA + 1);
591
592 /* Now fill in the name */
593 CopyMemory(Ptr, &Entry->if_descr[0], Entry->if_descrlen);
594 CurrentAA->AdapterName = (PCHAR)Ptr;
595 CurrentAA->AdapterName[Entry->if_descrlen] = '\0';
596 /* Next items */
597 Ptr = (BYTE*)(CurrentAA->AdapterName + Entry->if_descrlen + 1);
598
599 /* The DNS suffix */
600 CurrentAA->DnsSuffix = (PWCHAR)Ptr;
601
602 if (Entry->if_type != IF_TYPE_SOFTWARE_LOOPBACK)
603 {
604 HKEY InterfaceKey;
605 CHAR KeyName[256];
606 DWORD ValueType, ValueSize;
607
608 snprintf(KeyName, 256,
609 "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\%*s",
610 Entry->if_descrlen, &Entry->if_descr[0]);
611
613 {
614 if (DhcpDomainSize != 0)
615 {
616 ValueSize = DhcpDomainSize + sizeof(WCHAR);
617 if (RegQueryValueExW(InterfaceKey, L"DhcpDomain", NULL, &ValueType, (LPBYTE)CurrentAA->DnsSuffix, &ValueSize) == ERROR_SUCCESS &&
618 ValueType == REG_SZ && ValueSize == DhcpDomainSize + sizeof(WCHAR))
619 {
620 /* We're done, next items */
621 Ptr = (BYTE*)(CurrentAA->DnsSuffix + (ValueSize / sizeof(WCHAR)));
622 }
623 else
624 {
625 /* Fail */
626 ERR("DhcpDomain name changed after probe!\n");
627 DhcpDomainSize = 0;
628 }
629 }
630
631 if (DomainSize != 0)
632 {
633 ValueSize = DomainSize + sizeof(WCHAR);
634 if (RegQueryValueExW(InterfaceKey, L"Domain", NULL, &ValueType, (LPBYTE)CurrentAA->DnsSuffix, &ValueSize) == ERROR_SUCCESS &&
635 ValueType == REG_SZ && ValueSize == DomainSize + sizeof(WCHAR))
636 {
637 /* We're done, next items */
638 Ptr = (BYTE*)(CurrentAA->DnsSuffix + (ValueSize / sizeof(WCHAR)));
639 }
640 else
641 {
642 /* Fail */
643 ERR("Domain name changed after probe!\n");
644 DomainSize = 0;
645 }
646 }
647
648 RegCloseKey(InterfaceKey);
649 }
650 }
651
652 /* In case of failure (or no name) */
653 if ((DhcpDomainSize == 0) && (DomainSize == 0))
654 {
655 CurrentAA->DnsSuffix[0] = L'\0';
656 /* Next items */
657 Ptr = (BYTE*)(CurrentAA->DnsSuffix + 1);
658 }
659
660 /* The description */
661 CurrentAA->Description = (PWCHAR)Ptr;
662
663 if (DescriptionSize != 0)
664 {
665 if (Entry->if_type == IF_TYPE_SOFTWARE_LOOPBACK)
666 {
667 size_t size;
668 size = mbstowcs((PWCHAR)Ptr, (PCSTR)&Entry->if_descr[0], Entry->if_descrlen);
669 CurrentAA->Description = (PWCHAR)Ptr;
670 CurrentAA->Description[size] = '\0';
671 /* Next items */
672 Ptr = (BYTE*)(CurrentAA->Description + size + 1);
673 }
674 else
675 {
676 HKEY ConnectionKey;
677 CHAR KeyName[256];
678 CHAR InstanceID[128];
679 DWORD ValueType = 0;
680 DWORD ValueSize = 0;
681
682 snprintf(KeyName, 256,
683 "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\%*s\\Connection",
684 Entry->if_descrlen, &Entry->if_descr[0]);
685
687 {
688 ValueSize = 128;
689 RegQueryValueExA(ConnectionKey, "PnpInstanceID", NULL, &ValueType, (LPBYTE)InstanceID, &ValueSize);
690 RegCloseKey(ConnectionKey);
691 }
692
693 if (ValueSize != 0)
694 {
695 sprintf(KeyName, "SYSTEM\\CurrentControlSet\\Enum\\%s", InstanceID);
696
698 {
699 ValueSize = DescriptionSize + sizeof(WCHAR);
700 if (RegQueryValueExW(ConnectionKey, L"DeviceDesc", NULL, &ValueType, (LPBYTE)CurrentAA->Description, &ValueSize) == ERROR_SUCCESS &&
701 ValueType == REG_SZ && ValueSize == DescriptionSize + sizeof(WCHAR))
702 {
703 /* We're done, next items */
704 Ptr = (BYTE*)(CurrentAA->Description + (ValueSize / sizeof(WCHAR)));
705 }
706 else
707 {
708 /* Fail */
709 ERR("Description name changed after probe!\n");
710 DescriptionSize = 0;
711 }
712
713 RegCloseKey(ConnectionKey);
714 }
715 }
716 }
717 }
718
719 /* In case of failure (or no name) */
720 if (DescriptionSize == 0)
721 {
722 CurrentAA->Description[0] = L'\0';
723 /* Next items */
724 Ptr = (BYTE*)(CurrentAA->Description + 1);
725 }
726
727 /* The friendly name */
729 {
730 CurrentAA->FriendlyName = (PWCHAR)Ptr;
731
732 if (FriendlySize != 0)
733 {
734 /* Get the friendly name */
735 if (Entry->if_type == IF_TYPE_SOFTWARE_LOOPBACK)
736 {
737 size_t size;
738 size = mbstowcs(CurrentAA->FriendlyName, (PCSTR)&Entry->if_descr[0], Entry->if_descrlen);
739 CurrentAA->FriendlyName[size] = '\0';
740 /* Next items */
741 Ptr = (BYTE*)(CurrentAA->FriendlyName + size + 1);
742 }
743 else
744 {
745 HKEY ConnectionKey;
746 CHAR KeyName[256];
747
748 snprintf(KeyName, 256,
749 "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\%*s\\Connection",
750 Entry->if_descrlen, &Entry->if_descr[0]);
751
753 {
755 DWORD ValueSize = FriendlySize + sizeof(WCHAR);
756
757 if (RegQueryValueExW(ConnectionKey, L"Name", NULL, &ValueType, (LPBYTE)CurrentAA->FriendlyName, &ValueSize) == ERROR_SUCCESS &&
758 ValueType == REG_SZ && ValueSize == FriendlySize + sizeof(WCHAR))
759 {
760 /* We're done, next items */
761 Ptr = (BYTE*)(CurrentAA->FriendlyName + (ValueSize / sizeof(WCHAR)));
762 }
763 else
764 {
765 /* Fail */
766 ERR("Friendly name changed after probe!\n");
767 FriendlySize = 0;
768 }
769
770 RegCloseKey(ConnectionKey);
771 }
772 else
773 {
774 /* Fail */
775 FriendlySize = 0;
776 }
777 }
778 }
779
780 /* In case of failure (or no name) */
781 if (FriendlySize == 0)
782 {
783 CurrentAA->FriendlyName[0] = L'\0';
784 /* Next items */
785 Ptr = (BYTE*)(CurrentAA->FriendlyName + 1);
786 }
787 }
788
789 /* The DNS Servers */
790 if (!(Flags & GAA_FLAG_SKIP_DNS_SERVER))
791 {
792 /* Enumerate the name servers */
793 HKEY InterfaceKey;
794 CHAR KeyName[256];
795
796 snprintf(KeyName, 256,
797 "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\%*s",
798 Entry->if_descrlen, &Entry->if_descr[0]);
799
801 {
802 TRACE("Failed opening interface key for interface %*s\n", Entry->if_descrlen, &Entry->if_descr[0]);
803 }
804 else
805 {
806 PIP_ADAPTER_DNS_SERVER_ADDRESS* ServerAddressPtr;
807
808 CurrentAA->FirstDnsServerAddress = (PIP_ADAPTER_DNS_SERVER_ADDRESS)Ptr;
809 ServerAddressPtr = &CurrentAA->FirstDnsServerAddress;
810
811 EnumNameServers(InterfaceKey, NULL, &ServerAddressPtr, EnumerateServerName);
812 RegCloseKey(InterfaceKey);
813
814 /* Set the last entry in the list as having NULL next member */
815 Ptr = (BYTE*)*ServerAddressPtr;
816 *ServerAddressPtr = NULL;
817 }
818 }
819
820 /* We're done for this interface */
821 PreviousAA = CurrentAA;
822 RemainingSize -= CurrentAASize;
823 }
824 }
825 }
826
827 if (AdaptersCount == 0)
828 {
829 /* Uh? Not even localhost ?! */
830 ERR("No Adapters found!\n");
831 *pOutBufLen = 0;
832 return ERROR_NO_DATA;
833 }
834
835 /* See if we have anything to add */
836 // FIXME: Anycast and multicast
837 if ((Flags & (GAA_FLAG_SKIP_UNICAST | GAA_FLAG_INCLUDE_PREFIX)) == GAA_FLAG_SKIP_UNICAST)
838 goto Success;
839
840 /* Now fill in the addresses */
841 for (i = 0; i < InterfacesCount; i++)
842 {
843 /* Look for network layers */
844 if ((InterfacesList[i].tei_entity == CL_NL_ENTITY)
845 || (InterfacesList[i].tei_entity == CO_NL_ENTITY))
846 {
847 IPSNMPInfo SnmpInfo;
848 PIP_ADAPTER_ADDRESSES CurrentAA = NULL;
849 IPAddrEntry* AddrEntries;
850 ULONG j;
851
852 /* Get its SNMP info */
853 Status = GetSnmpInfo(TcpFile, InterfacesList[i], &SnmpInfo);
854 if (!NT_SUCCESS(Status))
855 goto Error;
856
857 if (SnmpInfo.ipsi_numaddr == 0)
858 continue;
859
860 /* Allocate the address entry array and get them */
861 AddrEntries = HeapAlloc(GetProcessHeap(),
863 SnmpInfo.ipsi_numaddr * sizeof(AddrEntries[0]));
864 if (!AddrEntries)
865 {
867 goto Error;
868 }
869 Status = GetAddrEntries(TcpFile, InterfacesList[i], AddrEntries, SnmpInfo.ipsi_numaddr);
870 if (!NT_SUCCESS(Status))
871 {
872 HeapFree(GetProcessHeap(), 0, AddrEntries);
873 goto Error;
874 }
875
876 for (j = 0; j < SnmpInfo.ipsi_numaddr; j++)
877 {
878 /* Find the adapters struct for this address. */
879 if (pAdapterAddresses)
880 {
881 CurrentAA = pAdapterAddresses;
882 while (CurrentAA)
883 {
884 if (CurrentAA->IfIndex == AddrEntries[j].iae_index)
885 break;
886
887 CurrentAA = CurrentAA->Next;
888 }
889
890 if (!CurrentAA)
891 {
892 ERR("Got address for interface %u but no adapter was found for it.\n", AddrEntries[j].iae_index);
893 /* Go to the next address */
894 continue;
895 }
896 }
897
898 TRACE("address is 0x%08x, mask is 0x%08x\n", AddrEntries[j].iae_addr, AddrEntries[j].iae_mask);
899
900 //FIXME: For now reactos only supports unicast addresses
902 {
903 ULONG Size = sizeof(IP_ADAPTER_UNICAST_ADDRESS) + sizeof(SOCKADDR);
904
905 if (Ptr && (RemainingSize >= Size))
906 {
907 PIP_ADAPTER_UNICAST_ADDRESS UnicastAddress = (PIP_ADAPTER_UNICAST_ADDRESS)Ptr;
908
909 /* Fill in the structure */
910 UnicastAddress->Length = sizeof(IP_ADAPTER_UNICAST_ADDRESS);
911 UnicastAddress->Next = CurrentAA->FirstUnicastAddress;
912
913 // FIXME: Put meaningful value here
914 UnicastAddress->Flags = 0;
915 UnicastAddress->PrefixOrigin = IpPrefixOriginOther;
916 UnicastAddress->SuffixOrigin = IpSuffixOriginOther;
917 UnicastAddress->DadState = IpDadStatePreferred;
918 UnicastAddress->ValidLifetime = 0xFFFFFFFF;
919 UnicastAddress->PreferredLifetime = 0xFFFFFFFF;
920
921 /* Set the address */
922 //FIXME: ipv4 only (again...)
923 UnicastAddress->Address.lpSockaddr = (LPSOCKADDR)(UnicastAddress + 1);
924 UnicastAddress->Address.iSockaddrLength = sizeof(SOCKADDR);
925 UnicastAddress->Address.lpSockaddr->sa_family = AF_INET;
926 ((LPSOCKADDR_IN)UnicastAddress->Address.lpSockaddr)->sin_port = 0;
927 memcpy(&((LPSOCKADDR_IN)UnicastAddress->Address.lpSockaddr)->sin_addr, &AddrEntries[j].iae_addr, sizeof(AddrEntries[j].iae_addr));
928
929 CurrentAA->FirstUnicastAddress = UnicastAddress;
930 Ptr += Size;
931 RemainingSize -= Size;
932 }
933
934 TotalSize += Size;
935 }
936
937 if (Flags & GAA_FLAG_INCLUDE_PREFIX)
938 {
939 ULONG Size = sizeof(IP_ADAPTER_PREFIX) + sizeof(SOCKADDR);
940
941 if (Ptr && (RemainingSize >= Size))
942 {
943 PIP_ADAPTER_PREFIX Prefix = (PIP_ADAPTER_PREFIX)Ptr;
944
945 /* Fill in the structure */
946 Prefix->Length = sizeof(IP_ADAPTER_PREFIX);
947 Prefix->Next = CurrentAA->FirstPrefix;
948
949 /* Set the address */
950 //FIXME: ipv4 only (again...)
951 Prefix->Address.lpSockaddr = (LPSOCKADDR)(Prefix + 1);
952 Prefix->Address.iSockaddrLength = sizeof(AddrEntries[j].iae_mask);
953 Prefix->Address.lpSockaddr->sa_family = AF_INET;
954 memcpy(Prefix->Address.lpSockaddr->sa_data, &AddrEntries[j].iae_mask, sizeof(AddrEntries[j].iae_mask));
955
956 /* Compute the prefix size */
957 _BitScanReverse(&Prefix->PrefixLength, AddrEntries[j].iae_mask);
958
959 CurrentAA->FirstPrefix = Prefix;
960 Ptr += Size;
961 RemainingSize -= Size;
962 }
963
964 TotalSize += Size;
965 }
966 }
967
968 HeapFree(GetProcessHeap(), 0, AddrEntries);
969 }
970 }
971
972Success:
973 /* We're done */
974 HeapFree(GetProcessHeap(), 0, InterfacesList);
975 NtClose(TcpFile);
976 *pOutBufLen = TotalSize;
977 TRACE("TotalSize: %x\n", *pOutBufLen);
978 return ERROR_SUCCESS;
979
980Error:
981 ERR("Failed! Status 0x%08x\n", Status);
982 *pOutBufLen = 0;
983 HeapFree(GetProcessHeap(), 0, InterfacesList);
984 NtClose(TcpFile);
986}
987#endif
Type
Definition: Type.h:7
#define DECLSPEC_HOTPATCH
Definition: _mingw.h:240
#define IP_MIB_STATS_ID
Definition: afd.h:35
#define IP_MIB_ADDRTABLE_ENTRY_ID
Definition: afd.h:36
#define WINE_DEFAULT_DEBUG_CHANNEL(t)
Definition: precomp.h:23
LONG NTSTATUS
Definition: precomp.h:26
#define CHAR(Char)
#define FIXME(fmt,...)
Definition: precomp.h:53
#define WARN(fmt,...)
Definition: precomp.h:61
#define ERR(fmt,...)
Definition: precomp.h:57
BOOL Error
Definition: chkdsk.c:66
#define RegCloseKey(hKey)
Definition: registry.h:49
#define STATUS_NO_MEMORY
Definition: d3dkmdt.h:51
#define BufferSize
Definition: mmc.h:75
#define ERROR_SUCCESS
Definition: deptool.c:10
#define NULL
Definition: types.h:112
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:33
LONG WINAPI RegOpenKeyExA(_In_ HKEY hKey, _In_ LPCSTR lpSubKey, _In_ DWORD ulOptions, _In_ REGSAM samDesired, _Out_ PHKEY phkResult)
Definition: reg.c:3298
LONG WINAPI RegQueryValueExA(_In_ HKEY hkeyorg, _In_ LPCSTR name, _In_ LPDWORD reserved, _Out_opt_ LPDWORD type, _Out_opt_ LPBYTE data, _Inout_opt_ LPDWORD count)
Definition: reg.c:4009
LONG WINAPI RegQueryValueExW(_In_ HKEY hkeyorg, _In_ LPCWSTR name, _In_ LPDWORD reserved, _In_ LPDWORD type, _In_ LPBYTE data, _In_ LPDWORD count)
Definition: reg.c:4103
#define GetProcessHeap()
Definition: compat.h:736
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define HeapAlloc
Definition: compat.h:733
#define HeapFree(x, y, z)
Definition: compat.h:735
#define HEAP_ZERO_MEMORY
Definition: compat.h:134
#define L(x)
Definition: resources.c:13
#define AF_INET
Definition: tcpip.h:117
TDIEntityInfo * EntityList
Definition: main.c:27
#define MIN_SIZE
Definition: mem.c:366
@ Success
Definition: eventcreate.c:712
unsigned long DWORD
Definition: ntddk_ex.h:95
_Must_inspect_result_ _In_ PFSRTL_PER_STREAM_CONTEXT Ptr
Definition: fsrtlfuncs.h:898
Status
Definition: gdiplustypes.h:25
GLsizeiptr size
Definition: glext.h:5919
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
@ IfOperStatusUp
Definition: ifdef.h:185
@ IfOperStatusDown
Definition: ifdef.h:186
#define MAX_ADAPTER_DESCRIPTION_LENGTH
Definition: iinfo.c:16
NTSYSAPI ULONG WINAPI RtlNtStatusToDosError(NTSTATUS)
unsigned char _BitScanReverse(unsigned long *_Index, unsigned long _Mask)
Definition: intrin_arm.h:180
static PIP_ADAPTER_ADDRESSES
Definition: iphlpapi.c:76
#define GAA_FLAG_SKIP_FRIENDLY_NAME
#define GAA_FLAG_SKIP_UNICAST
LSTATUS EnumNameServers(HKEY RegHandle, LPWSTR Interface, PVOID Data, EnumNameServersFunc cb)
@ IF_OPER_STATUS_CONNECTING
Definition: ipifcons.h:241
#define IF_TYPE_SOFTWARE_LOOPBACK
Definition: ipifcons.h:44
#define RTL_FIELD_SIZE(type, field)
Definition: kdb_expr.c:86
#define REG_SZ
Definition: layer.c:22
#define ZeroMemory
Definition: minwinbase.h:31
#define CopyMemory
Definition: minwinbase.h:29
#define PCHAR
Definition: match.c:90
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
static const ENTRY Entries[]
#define sprintf(buf, format,...)
Definition: sprintf.c:55
@ IpDadStatePreferred
Definition: nldef.h:49
@ IpPrefixOriginOther
Definition: nldef.h:9
@ IpSuffixOriginOther
Definition: nldef.h:30
#define _Inout_
Definition: no_sal2.h:162
#define _Out_
Definition: no_sal2.h:160
#define _In_
Definition: no_sal2.h:158
#define FILE_READ_DATA
Definition: nt_native.h:628
#define KEY_READ
Definition: nt_native.h:1023
NTSYSAPI NTSTATUS NTAPI NtDeviceIoControlFile(IN HANDLE hFile, IN HANDLE hEvent OPTIONAL, IN PIO_APC_ROUTINE IoApcRoutine OPTIONAL, IN PVOID IoApcContext OPTIONAL, OUT PIO_STATUS_BLOCK pIoStatusBlock, IN ULONG DeviceIoControlCode, IN PVOID InBuffer OPTIONAL, IN ULONG InBufferLength, OUT PVOID OutBuffer OPTIONAL, IN ULONG OutBufferLength)
NTSTATUS NTAPI NtClose(IN HANDLE Handle)
Definition: obhandle.c:3402
#define DWORD
Definition: nt_native.h:44
NTSYSAPI NTSTATUS NTAPI NtWaitForSingleObject(IN HANDLE hObject, IN BOOLEAN bAlertable, IN PLARGE_INTEGER Timeout)
#define UNREFERENCED_PARAMETER(P)
Definition: ntbasedef.h:329
static int Family
Definition: ping.c:62
INT WSAAPI WSAStringToAddressW(IN LPWSTR AddressString, IN INT AddressFamily, IN LPWSAPROTOCOL_INFOW lpProtocolInfo, OUT LPSOCKADDR lpAddress, IN OUT LPINT lpAddressLength)
Definition: rnr.c:977
#define REG_DWORD
Definition: sdbapi.c:598
mbstowcs
Definition: stdlib.h:925
NTSTATUS openTcpFile(PHANDLE tcpFile, ACCESS_MASK DesiredAccess)
Definition: handle.c:12
#define TRACE(s)
Definition: solgame.cpp:4
base of all file and directory entries
Definition: entries.h:83
ULONG iae_mask
Definition: tcpioctl.h:167
ULONG ipsi_numaddr
Definition: tcpioctl.h:159
unsigned short Length
Definition: sprintf.c:451
ULONG tei_entity
Definition: tdiinfo.h:31
ULONG tei_instance
Definition: tdiinfo.h:32
ULONG toi_id
Definition: tdiinfo.h:77
ULONG toi_type
Definition: tdiinfo.h:76
ULONG toi_class
Definition: tdiinfo.h:75
TDIEntityID toi_entity
Definition: tdiinfo.h:74
#define IF_ENTITY
Definition: tdiinfo.h:47
#define ENTITY_LIST_ID
Definition: tdiinfo.h:38
#define CO_NL_ENTITY
Definition: tdiinfo.h:44
struct _TDIEntityID TDIEntityID
#define INFO_CLASS_PROTOCOL
Definition: tdiinfo.h:65
#define INFO_CLASS_GENERIC
Definition: tdiinfo.h:64
#define INFO_TYPE_PROVIDER
Definition: tdiinfo.h:69
#define GENERIC_ENTITY
Definition: tdiinfo.h:37
#define CL_NL_ENTITY
Definition: tdiinfo.h:42
#define IOCTL_TCP_QUERY_INFORMATION_EX
Definition: tditest.h:110
#define STATUS_PENDING
Definition: telnetd.h:14
uint32_t * PULONG
Definition: typedefs.h:59
#define FIELD_OFFSET(t, f)
Definition: typedefs.h:255
unsigned char * LPBYTE
Definition: typedefs.h:53
void * PVOID
Definition: typedefs.h:50
uint32_t * LPDWORD
Definition: typedefs.h:59
const char * PCSTR
Definition: typedefs.h:52
uint32_t ULONG_PTR
Definition: typedefs.h:65
uint16_t * PWCHAR
Definition: typedefs.h:56
unsigned char * PUCHAR
Definition: typedefs.h:53
uint32_t ULONG
Definition: typedefs.h:59
_Must_inspect_result_ _In_ WDFCHILDLIST _In_ PWDF_CHILD_LIST_ITERATOR _Out_ WDFDEVICE _Inout_opt_ PWDF_CHILD_RETRIEVE_INFO Info
Definition: wdfchildlist.h:690
_Must_inspect_result_ _In_ WDFDEVICE _In_ PWDF_DEVICE_PROPERTY_DATA _In_ DEVPROPTYPE _In_ ULONG Size
Definition: wdfdevice.h:4533
_Must_inspect_result_ _In_ WDFDEVICE _In_ PCUNICODE_STRING KeyName
Definition: wdfdevice.h:2699
_Must_inspect_result_ _In_ WDFDEVICE _In_ LPCGUID _Out_ PINTERFACE Interface
Definition: wdffdo.h:465
_In_ WDFMEMORY _Out_opt_ size_t * BufferSize
Definition: wdfmemory.h:254
_Must_inspect_result_ _In_ PWDFDEVICE_INIT _In_ PCUNICODE_STRING InstanceID
Definition: wdfpdo.h:309
_Must_inspect_result_ _In_ WDFKEY _In_ PCUNICODE_STRING _In_ ULONG _Out_opt_ PULONG _Out_opt_ PULONG ValueType
Definition: wdfregistry.h:282
_Reserved_ PVOID Reserved
Definition: winddi.h:3974
#define WINAPI
Definition: msvc.h:6
#define ERROR_BUFFER_OVERFLOW
Definition: winerror.h:307
#define ERROR_NO_DATA
Definition: winerror.h:406
#define HKEY_LOCAL_MACHINE
Definition: winreg.h:12
struct sockaddr_in * LPSOCKADDR_IN
Definition: winsock.h:489
#define AF_INET6
Definition: winsock.h:369
struct sockaddr * LPSOCKADDR
Definition: winsock.h:486
struct sockaddr SOCKADDR
Definition: winsock.h:484
#define AF_UNSPEC
Definition: winsock.h:344
#define snprintf
Definition: wintirpc.h:48
_Must_inspect_result_ _In_ ULONG Flags
Definition: wsk.h:170
_In_ __drv_aliasesMem PSTRING Prefix
Definition: rtlfuncs.h:1647
__wchar_t WCHAR
Definition: xmlstorage.h:180
char CHAR
Definition: xmlstorage.h:175
unsigned char BYTE
Definition: xxhash.c:193