windows-nt/Source/XPSP1/NT/net/config/common/ncnetcfg/kkenet.cpp
2020-09-26 16:20:57 +08:00

250 lines
6.5 KiB
C++

//+---------------------------------------------------------------------------
//
// Microsoft Windows
// Copyright (C) Microsoft Corporation, 1997.
//
// File: K K E N E T . C P P
//
// Contents: Ethernet address function
//
// Notes:
//
// Author: kumarp
//
//----------------------------------------------------------------------------
#include "pch.h"
#pragma hdrstop
#include "kkutils.h"
#include "ndispnp.h"
#include "ntddndis.h" // This defines the IOCTL constants.
extern const WCHAR c_szDevice[];
HRESULT HrGetNetCardAddr(IN PCWSTR pszDriver, OUT ULONGLONG* pqwNetCardAddr)
{
AssertValidReadPtr(pszDriver);
AssertValidWritePtr(pqwNetCardAddr);
DefineFunctionName("HrGetNetCardAddr");
HRESULT hr = S_OK;
// Form the device name in form "\Device\{GUID}"
tstring strDeviceName = c_szDevice;
strDeviceName.append(pszDriver);
UNICODE_STRING ustrDevice;
::RtlInitUnicodeString(&ustrDevice, strDeviceName.c_str());
UINT uiRet;
UCHAR MacAddr[6];
UCHAR PMacAddr[6];
UCHAR VendorId[3];
ULONGLONG qw = 0;
uiRet = NdisQueryHwAddress(&ustrDevice, MacAddr, PMacAddr, VendorId);
if (uiRet)
{
for (int i=0; i<=4; i++)
{
qw |= MacAddr[i];
qw <<= 8;
}
qw |= MacAddr[i];
}
else
{
hr = HrFromLastWin32Error();
}
*pqwNetCardAddr = qw;
TraceError(__FUNCNAME__, hr);
return hr;
}
//+---------------------------------------------------------------------------
//
// Function: HrGetNetCardAddrOld
//
// Purpose: Get mac address of a netcard without using NdisQueryHwAddress
//
// Arguments:
// pszDriver [in] name (on NT3.51/4) or guid (on NT5) of driver
// pqwNetCardAddr [out] pointer to result
//
// Returns: S_OK on success, otherwise an error code
//
// Author: kumarp 11-February-99
//
// Notes:
//
#define DEVICE_PREFIX L"\\\\.\\"
HRESULT HrGetNetCardAddrOld(IN PCWSTR pszDriver, OUT ULONGLONG* pqwNetCardAddr)
{
DefineFunctionName("HrGetNetCardAddrOld");
AssertValidReadPtr(pszDriver);
*pqwNetCardAddr = 0;
WCHAR LinkName[512];
WCHAR DeviceName[80];
WCHAR szMACFileName[80];
WCHAR OidData[4096];
BOOL fCreatedDevice = FALSE;
DWORD ReturnedCount;
HANDLE hMAC;
HRESULT hr = S_OK;
NDIS_OID OidCode[] =
{
OID_802_3_PERMANENT_ADDRESS, // Ethernet
OID_802_5_PERMANENT_ADDRESS, // TokenRing
OID_FDDI_LONG_PERMANENT_ADDR, // FDDI
};
//
// Check to see if the DOS name for the MAC driver already exists.
// Its not created automatically in version 3.1 but may be later.
//
TraceTag (ttidDefault, "Attempting to get address of %S", pszDriver);
if (QueryDosDevice(pszDriver, LinkName, sizeof(LinkName)) == 0)
{
if (ERROR_FILE_NOT_FOUND == GetLastError())
{
wcscpy(DeviceName, L"\\Device\\");
wcscat(DeviceName, pszDriver);
//
// It doesn't exist so create it.
//
if (DefineDosDevice( DDD_RAW_TARGET_PATH, pszDriver, DeviceName))
{
fCreatedDevice = TRUE;
}
else
{
TraceLastWin32Error("DefineDosDevice returned an error creating the device");
hr = HrFromLastWin32Error();
}
}
else
{
TraceLastWin32Error("QueryDosDevice returned an error");
hr = HrFromLastWin32Error();
}
}
if (S_OK == hr)
{
//
// Construct a device name to pass to CreateFile
//
wcscpy(szMACFileName, DEVICE_PREFIX);
wcscat(szMACFileName, pszDriver);
hMAC = CreateFile(
szMACFileName,
GENERIC_READ,
FILE_SHARE_READ | FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
0,
INVALID_HANDLE_VALUE
);
if (hMAC != INVALID_HANDLE_VALUE)
{
DWORD count = 0;
DWORD ReturnedCount = 0;
//
// We successfully opened the driver, format the IOCTL to pass the
// driver.
//
while ((0 == ReturnedCount) && (count < celems (OidCode)))
{
if (DeviceIoControl(
hMAC,
IOCTL_NDIS_QUERY_GLOBAL_STATS,
&OidCode[count],
sizeof(OidCode[count]),
OidData,
sizeof(OidData),
&ReturnedCount,
NULL
))
{
TraceTag (ttidDefault, "OID %lX succeeded", OidCode[count]);
if (ReturnedCount == 6)
{
*pqwNetCardAddr = (ULONGLONG) 0;
WORD wAddrLen=6;
for (int i=0; i<wAddrLen; i++)
{
*(((BYTE*) pqwNetCardAddr)+i) = *(((BYTE*) OidData)+(wAddrLen-i-1));
}
hr = S_OK;
}
else
{
TraceLastWin32Error("DeviceIoControl returned an invalid count");
hr = HrFromLastWin32Error();
}
}
else
{
hr = HrFromLastWin32Error();
}
count++;
}
}
else
{
TraceLastWin32Error("CreateFile returned an error");
hr = HrFromLastWin32Error();
}
}
if (fCreatedDevice)
{
//
// The MAC driver wasn't visible in the Win32 name space so we created
// a link. Now we have to delete it.
//
if (!DefineDosDevice(
DDD_RAW_TARGET_PATH | DDD_REMOVE_DEFINITION |
DDD_EXACT_MATCH_ON_REMOVE,
pszDriver,
DeviceName)
)
{
TraceLastWin32Error("DefineDosDevice returned an error removing the device");
}
}
TraceFunctionError(hr);
return hr;
}
#ifdef DBG
void PrintNetCardAddr(IN PCWSTR pszDriver)
{
ULONGLONG qwNetCardAddr=0;
HRESULT hr = HrGetNetCardAddr(pszDriver, &qwNetCardAddr);
wprintf(L"Netcard address for %s: 0x%012.12I64x", pszDriver, qwNetCardAddr);
TraceError("dafile.main", hr);
}
#endif // DBG