216 lines
5.6 KiB
C
216 lines
5.6 KiB
C
|
/*++
|
||
|
|
||
|
Copyright (c) 1994 Microsoft Corporation
|
||
|
|
||
|
Module Name:
|
||
|
|
||
|
wins.c
|
||
|
|
||
|
Abstract:
|
||
|
|
||
|
Functions to retrieve info from NetBT device driver
|
||
|
|
||
|
Contents:
|
||
|
GetWinsServers
|
||
|
|
||
|
Author:
|
||
|
|
||
|
Richard L Firth (rfirth) 6-Aug-1994
|
||
|
|
||
|
Revision History:
|
||
|
|
||
|
rfirth 6-Aug-1994
|
||
|
Created
|
||
|
|
||
|
--*/
|
||
|
|
||
|
#include "precomp.h"
|
||
|
#include <nbtioctl.h>
|
||
|
|
||
|
//
|
||
|
// seems that if WINS addresses not specified, NetBT reports 127.0.0.0 so if
|
||
|
// this value is returned, we won't display them
|
||
|
//
|
||
|
|
||
|
#define LOCAL_WINS_ADDRESS 0x0000007f // 127.0.0.0
|
||
|
|
||
|
#define BYTE_SWAP(w) (HIBYTE(w) | (LOBYTE(w) << 8))
|
||
|
#define WORD_SWAP(d) (BYTE_SWAP(HIWORD(d)) | (BYTE_SWAP(LOWORD(d)) << 16))
|
||
|
|
||
|
/*******************************************************************************
|
||
|
*
|
||
|
* GetWinsServers
|
||
|
*
|
||
|
* Gets the primary and secondary WINS addresses for a particular adapter from
|
||
|
* NetBT
|
||
|
*
|
||
|
* ENTRY AdapterInfo - pointer to ADAPTER_INFO
|
||
|
*
|
||
|
* EXIT AdapterInfo.PrimaryWinsServer and AdapterInfo.SecondaryWinsServer
|
||
|
*
|
||
|
* RETURNS TRUE if success
|
||
|
*
|
||
|
* ASSUMES 1.
|
||
|
* 2. We have already got the Node Type for this adapter
|
||
|
*
|
||
|
******************************************************************************/
|
||
|
|
||
|
BOOL GetWinsServers(PIP_ADAPTER_INFO AdapterInfo)
|
||
|
{
|
||
|
|
||
|
HANDLE h;
|
||
|
OBJECT_ATTRIBUTES objAttr;
|
||
|
IO_STATUS_BLOCK iosb;
|
||
|
STRING name;
|
||
|
UNICODE_STRING uname;
|
||
|
NTSTATUS status;
|
||
|
DWORD i;
|
||
|
tWINS_NODE_INFO winsInfo;
|
||
|
char path[MAX_PATH];
|
||
|
|
||
|
//
|
||
|
// default the 'have WINS' status of this adapter
|
||
|
//
|
||
|
|
||
|
AdapterInfo->HaveWins = FALSE;
|
||
|
|
||
|
strcpy(path, "\\Device\\NetBT_Tcpip_");
|
||
|
strcat(path, AdapterInfo->AdapterName);
|
||
|
|
||
|
RtlInitString(&name, path);
|
||
|
status = RtlAnsiStringToUnicodeString(&uname, &name, TRUE);
|
||
|
if (!NT_SUCCESS(status)) {
|
||
|
DEBUG_PRINT(("GetWinsServers: RtlAnsiStringToUnicodeString(name=%s) failed, err=%d\n",
|
||
|
name, GetLastError() ));
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
InitializeObjectAttributes(
|
||
|
&objAttr,
|
||
|
&uname,
|
||
|
OBJ_CASE_INSENSITIVE,
|
||
|
(HANDLE)NULL,
|
||
|
(PSECURITY_DESCRIPTOR)NULL
|
||
|
);
|
||
|
|
||
|
status = NtCreateFile(&h,
|
||
|
SYNCHRONIZE | FILE_READ_DATA | FILE_WRITE_DATA,
|
||
|
&objAttr,
|
||
|
&iosb,
|
||
|
NULL,
|
||
|
FILE_ATTRIBUTE_NORMAL,
|
||
|
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||
|
FILE_OPEN_IF,
|
||
|
0,
|
||
|
NULL,
|
||
|
0
|
||
|
);
|
||
|
|
||
|
RtlFreeUnicodeString(&uname);
|
||
|
|
||
|
if (!NT_SUCCESS(status)) {
|
||
|
DEBUG_PRINT(("GetWinsServers: NtCreateFile(path=%s) failed, err=%d\n",
|
||
|
path, GetLastError() ));
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
status = NtDeviceIoControlFile(h,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
NULL,
|
||
|
&iosb,
|
||
|
IOCTL_NETBT_GET_WINS_ADDR,
|
||
|
NULL,
|
||
|
0,
|
||
|
(PVOID)&winsInfo,
|
||
|
sizeof(winsInfo)
|
||
|
);
|
||
|
|
||
|
if (status == STATUS_PENDING) {
|
||
|
status = NtWaitForSingleObject(h, TRUE, NULL);
|
||
|
if (NT_SUCCESS(status)) {
|
||
|
status = iosb.Status;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
NtClose(h);
|
||
|
|
||
|
if (!NT_SUCCESS(status)) {
|
||
|
DEBUG_PRINT(("GetWinsServers: NtDeviceIoControlFile failed, err=%d\n",
|
||
|
GetLastError() ));
|
||
|
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// for some reason, NetBT returns the addresses in low-byte order. We have
|
||
|
// to swap them
|
||
|
//
|
||
|
|
||
|
for (i = 0; i < RTL_NUMBER_OF(winsInfo.AllNameServers); i++) {
|
||
|
winsInfo.AllNameServers[i] =
|
||
|
RtlUlongByteSwap(winsInfo.AllNameServers[i]);
|
||
|
}
|
||
|
|
||
|
DEBUG_PRINT(("GetWinsServers: Primary Address = %d.%d.%d.%d\n",
|
||
|
((LPBYTE)&winsInfo.AllNameServers[0])[0],
|
||
|
((LPBYTE)&winsInfo.AllNameServers[0])[1],
|
||
|
((LPBYTE)&winsInfo.AllNameServers[0])[2],
|
||
|
((LPBYTE)&winsInfo.AllNameServers[0])[3]
|
||
|
));
|
||
|
|
||
|
DEBUG_PRINT(("GetWinsServers: Secondary Address = %d.%d.%d.%d\n",
|
||
|
((LPBYTE)&winsInfo.AllNameServers[1])[0],
|
||
|
((LPBYTE)&winsInfo.AllNameServers[1])[1],
|
||
|
((LPBYTE)&winsInfo.AllNameServers[1])[2],
|
||
|
((LPBYTE)&winsInfo.AllNameServers[1])[3]
|
||
|
));
|
||
|
|
||
|
//
|
||
|
// if we get 127.0.0.0 back then convert it to the NULL address. See
|
||
|
// ASSUMES in function header
|
||
|
//
|
||
|
|
||
|
if (winsInfo.AllNameServers[0] == LOCAL_WINS_ADDRESS) {
|
||
|
winsInfo.AllNameServers[0] = 0;
|
||
|
} else {
|
||
|
AdapterInfo->HaveWins = TRUE;
|
||
|
}
|
||
|
AddIpAddress(&AdapterInfo->PrimaryWinsServer,
|
||
|
winsInfo.AllNameServers[0],
|
||
|
0,
|
||
|
0
|
||
|
);
|
||
|
|
||
|
//
|
||
|
// same with secondary
|
||
|
//
|
||
|
|
||
|
if (winsInfo.AllNameServers[1] == LOCAL_WINS_ADDRESS) {
|
||
|
winsInfo.AllNameServers[1] = 0;
|
||
|
} else {
|
||
|
AdapterInfo->HaveWins = TRUE;
|
||
|
}
|
||
|
AddIpAddress(&AdapterInfo->SecondaryWinsServer,
|
||
|
winsInfo.AllNameServers[1],
|
||
|
0,
|
||
|
0
|
||
|
);
|
||
|
|
||
|
//
|
||
|
// Append any remaining addresses.
|
||
|
//
|
||
|
|
||
|
for (i = 0; i < winsInfo.NumOtherServers; i++) {
|
||
|
if (winsInfo.Others[i] != LOCAL_WINS_ADDRESS) {
|
||
|
AddIpAddress(&AdapterInfo->SecondaryWinsServer,
|
||
|
winsInfo.Others[i],
|
||
|
0,
|
||
|
0
|
||
|
);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return TRUE;
|
||
|
}
|