killvxk之前分享了一個代碼
https://bbs.pediy.com/thread-226472.htm
可惜發(fā)現(xiàn)晚了尿扯,那個連接無效了粱玲,只好自己擼了一個
調(diào)試上比較簡單拿著processmonitor 配合vm建一些快照,看看日志,就完事了空幻。
然后就是擼代碼蚕钦。
代碼中有個bug沧卢,其實也不算bug讥脐,沒準(zhǔn)還是個優(yōu)勢。
不過對于 xx 項目來說幔戏,NDIS Filter 太復(fù)雜了玛追,WFP 比較簡單,最后項目還是選擇WFP
/*
mengxp works 2020
QQ: 4003032
*/
#define _CRT_SECURE_NO_WARNINGS
#include <winsock2.h>
#include <netioapi.h>
#include <stdio.h>
#include <Shlwapi.h>
#include <setupapi.h>
#pragma comment(lib, "setupapi.lib")
#pragma comment(lib, "iphlpapi.lib")
DWORD OsVerMajor,OsVerMinor,OsVerWorkstation;
BOOL Is64BitWindows;
typedef BOOL (WINAPI *PISWOW64)(HANDLE hProcess,PBOOL pIsWow64);
typedef BOOL (WINAPI *PDISABLE_FS_REDIR)(PVOID *OldValue);
typedef BOOL (WINAPI *PREVERT_FS_REDIR)(PVOID OldValue);
typedef NTSTATUS (WINAPI *PFN_RTL_ADJUST_PRIVILEGE)(int, BOOL, BOOL, int *);
#define SE_DEBUG_PRIVILEGE 0x14
typedef enum tagCOMPONENT_CHARACTERISTICS {
NCF_VIRTUAL = 0x1,
NCF_SOFTWARE_ENUMERATED = 0x2,
NCF_PHYSICAL = 0x4,
NCF_HIDDEN = 0x8,
NCF_NO_SERVICE = 0x10,
NCF_NOT_USER_REMOVABLE = 0x20,
NCF_MULTIPORT_INSTANCED_ADAPTER = 0x40,
NCF_HAS_UI = 0x80,
NCF_SINGLE_INSTANCE = 0x100,
NCF_FILTER = 0x400,
NCF_DONTEXPOSELOWER = 0x1000,
NCF_HIDE_BINDING = 0x2000,
NCF_NDIS_PROTOCOL = 0x4000,
NCF_FIXED_BINDING = 0x20000,
NCF_LW_FILTER = 0x40000
} COMPONENT_CHARACTERISTICS;
VOID GetOsVer()
{
HMODULE hKernel32 = LoadLibraryA("Kernel32.dll");
PISWOW64 pfnIsWow64Process = (PISWOW64)GetProcAddress(hKernel32,"IsWow64Process");
BOOL bIsWow64 = FALSE;
OSVERSIONINFOEX OsVer;
memset(&OsVer,0,sizeof(OsVer));
OsVer.dwOSVersionInfoSize = sizeof(OsVer);
GetVersionEx((OSVERSIONINFO *)&OsVer);
OsVerMajor = OsVer.dwMajorVersion;
OsVerMinor = OsVer.dwMinorVersion;
OsVerWorkstation = OsVer.wProductType == VER_NT_WORKSTATION ? TRUE : FALSE;
if(pfnIsWow64Process)
pfnIsWow64Process(GetCurrentProcess(),&Is64BitWindows);
}
VOID AdjustDebugPrivilege()
{
HMODULE hNtDll = LoadLibraryA("ntdll.dll");
PFN_RTL_ADJUST_PRIVILEGE RtlAdjustPrivilege = (PFN_RTL_ADJUST_PRIVILEGE)GetProcAddress(hNtDll,"RtlAdjustPrivilege");
int Enabled;
RtlAdjustPrivilege(SE_DEBUG_PRIVILEGE, TRUE, FALSE, &Enabled);
}
BOOL ShutdownWow64Redir(PVOID *ppOldFsRedir)
{
HMODULE hKernel32 = LoadLibraryA("Kernel32.dll");
PISWOW64 pfnIsWow64Process = (PISWOW64)GetProcAddress(hKernel32,"IsWow64Process");
PDISABLE_FS_REDIR pfnDisableFsRedir = (PDISABLE_FS_REDIR)GetProcAddress(hKernel32,"Wow64DisableWow64FsRedirection");
PREVERT_FS_REDIR pfnRevertFsRedir = (PREVERT_FS_REDIR)GetProcAddress(hKernel32,"Wow64RevertWow64FsRedirection");
BOOL bIsWow64 = FALSE;
BOOL bRet = FALSE;
if(pfnIsWow64Process)
pfnIsWow64Process(GetCurrentProcess(),&bIsWow64);
if(bIsWow64 && pfnDisableFsRedir)
{
bRet = pfnDisableFsRedir(ppOldFsRedir);
}
return bRet;
}
BOOL RevertWow64Redir(PVOID pOldFsRedir)
{
HMODULE hKernel32 = LoadLibraryA("Kernel32.dll");
PISWOW64 pfnIsWow64Process = (PISWOW64)GetProcAddress(hKernel32,"IsWow64Process");
PDISABLE_FS_REDIR pfnDisableFsRedir = (PDISABLE_FS_REDIR)GetProcAddress(hKernel32,"Wow64DisableWow64FsRedirection");
PREVERT_FS_REDIR pfnRevertFsRedir = (PREVERT_FS_REDIR)GetProcAddress(hKernel32,"Wow64RevertWow64FsRedirection");
BOOL bIsWow64 = FALSE;
BOOL bRet = FALSE;
if(pfnIsWow64Process)
pfnIsWow64Process(GetCurrentProcess(),&bIsWow64);
if(bIsWow64 && pfnRevertFsRedir)
{
bRet = pfnRevertFsRedir(pOldFsRedir);
}
return bRet;
}
//////////////////////////////////////////////////////////////////////////
BOOL _IsServiceRunning(LPCSTR ServiceName)
{
SC_HANDLE hSc = NULL, hService = NULL;
BOOL bRunning = FALSE;
do {
SERVICE_STATUS Status;
hSc = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
if(!hSc)
break;
hService = OpenServiceA(hSc, ServiceName, SERVICE_ALL_ACCESS);
if(!hService)
break;
if(!QueryServiceStatus(hService, &Status))
break;
if(Status.dwCurrentState != SERVICE_STOPPED)
bRunning = TRUE;
} while (FALSE);
if(hSc)
CloseServiceHandle(hSc);
if(hService)
CloseServiceHandle(hService);
return bRunning;
}
BOOL _StartService(LPCSTR ServiceName)
{
SC_HANDLE hSc = NULL, hService = NULL;
BOOL bSuccess = FALSE;
do {
hSc = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
if(!hSc)
break;
hService = OpenServiceA(hSc, ServiceName, SERVICE_ALL_ACCESS);
if(!hService)
break;
bSuccess = StartService(hService, 0, NULL);
} while (FALSE);
if(hSc)
CloseServiceHandle(hSc);
if(hService)
CloseServiceHandle(hService);
return bSuccess;
}
BOOL _CreateService(LPCSTR ServiceName, LPCSTR DisplayName, LPCSTR SysPath, BOOL bKernelService, BOOL bAutoStart, LPCSTR LoadOrder)
{
SC_HANDLE hSc = NULL, hService = NULL;
BOOL bSuccess = FALSE;
do {
hSc = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
if(!hSc)
break;
hService = CreateServiceA(hSc, ServiceName, DisplayName, SERVICE_ALL_ACCESS,
bKernelService ? SERVICE_KERNEL_DRIVER : SERVICE_WIN32_OWN_PROCESS,
bAutoStart ? (bKernelService ? SERVICE_SYSTEM_START : SERVICE_AUTO_START) : SERVICE_DEMAND_START,
SERVICE_ERROR_IGNORE,
SysPath, LoadOrder, NULL, NULL, NULL, NULL);
if(!hService)
break;
bSuccess = TRUE;
} while (FALSE);
if(hSc)
CloseServiceHandle(hSc);
if(hService)
CloseServiceHandle(hService);
return bSuccess;
}
BOOL _DeleteService(LPCSTR ServiceName)
{
SC_HANDLE hSc = NULL, hService = NULL;
BOOL bSuccess = FALSE;
do {
hSc = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
if(!hSc)
break;
hService = OpenServiceA(hSc, ServiceName, SERVICE_ALL_ACCESS);
if(!hService)
break;
bSuccess = DeleteService(hService);
} while (FALSE);
if(hSc)
CloseServiceHandle(hSc);
if(hService)
CloseServiceHandle(hService);
return bSuccess;
}
BOOL _StopService(LPCSTR ServiceName)
{
SC_HANDLE hSc = NULL, hService = NULL;
BOOL bSuccess = FALSE;
do {
SERVICE_STATUS Status;
int i = 5;
hSc = OpenSCManager(NULL,NULL,SC_MANAGER_ALL_ACCESS);
if(!hSc)
break;
hService = OpenServiceA(hSc, ServiceName, SERVICE_ALL_ACCESS);
if(!hService)
break;
if(!ControlService(hService, SERVICE_CONTROL_STOP, &Status))
break;
if(Status.dwCurrentState == SERVICE_STOPPED)
{
bSuccess = TRUE;
break;
}
while(i--)
{
if(!QueryServiceStatus(hService, &Status))
break;
if(Status.dwCurrentState == SERVICE_STOPPED)
{
bSuccess = TRUE;
break;
}
}
} while (FALSE);
if(hSc)
CloseServiceHandle(hSc);
if(hService)
CloseServiceHandle(hService);
return bSuccess;
}
//////////////////////////////////////////////////////////////////////////
BOOL RegWow64;
LSTATUS QueryRegValue(HKEY key, LPCSTR subKey, LPCSTR name, LPBYTE value, ULONG *size, ULONG *type)
{
HKEY hKey;
LSTATUS Status;
REGSAM sam = KEY_QUERY_VALUE;
if(Is64BitWindows && RegWow64)
sam |= KEY_WOW64_64KEY;
Status = RegOpenKeyExA(key, subKey, 0, sam, &hKey);
if(Status == ERROR_SUCCESS)
{
Status = RegQueryValueExA(hKey, name, NULL, type, value, size);
RegCloseKey(hKey);
}
return Status;
}
LSTATUS QueryRegString(HKEY key, LPCSTR subKey, LPCSTR name, LPBYTE valueBuf, ULONG valueBufSize)
{
DWORD type;
return QueryRegValue(key, subKey, name, valueBuf, &valueBufSize, &type);
}
LSTATUS QueryRegDWORD(HKEY key, LPCSTR subKey, LPCSTR name, DWORD *value)
{
DWORD size = sizeof(DWORD), type;
return QueryRegValue(key, subKey, name, (LPBYTE)value, &size, &type);
}
LSTATUS SetRegValue(HKEY key, LPCSTR subKey, LPCSTR name, LPCBYTE value, ULONG size, ULONG type)
{
HKEY hKey;
LSTATUS Status;
REGSAM sam = KEY_ALL_ACCESS;
if(Is64BitWindows && RegWow64)
sam |= KEY_WOW64_64KEY;
Status = RegOpenKeyExA(key, subKey, 0, sam, &hKey);
if(Status == ERROR_SUCCESS)
{
Status = RegSetValueExA(hKey, name, 0, type, value, size);
RegCloseKey(hKey);
}
return Status;
}
LSTATUS SetRegString(HKEY key, LPCSTR subKey, LPCSTR name, LPCSTR value)
{
return SetRegValue(key, subKey, name, (LPCBYTE)value, strlen(value) + 1, REG_SZ);
}
LSTATUS SetRegMultiString1(HKEY key, LPCSTR subKey, LPCSTR name, LPCSTR value)
{
LSTATUS Status;
int bufSize = strlen(value) + 2;
char *buf;
buf = malloc(bufSize);
if(!buf)
return S_FALSE;
memset(buf, 0, bufSize);
strcpy(buf, value);
Status = SetRegValue(key, subKey, name, (LPCBYTE)buf, bufSize, REG_MULTI_SZ);
free(buf);
return Status;
}
LSTATUS SetRegDWORD(HKEY key, LPCSTR subKey, LPCSTR name, DWORD value)
{
return SetRegValue(key, subKey, name, (LPCBYTE)&value, sizeof(DWORD), REG_DWORD);
}
LSTATUS AppendRegMultiString(HKEY key, LPCSTR subKey, LPCSTR name, LPCSTR append)
{
HKEY hKey;
LSTATUS Status;
REGSAM sam = KEY_ALL_ACCESS;
if(Is64BitWindows && RegWow64)
sam |= KEY_WOW64_64KEY;
Status = RegOpenKeyExA(key, subKey, 0, sam, &hKey);
if(Status == ERROR_SUCCESS)
{
DWORD bufferIncrement = 4096, bufferSize, type, isExist = FALSE;
LPBYTE buffer;
PCHAR src, dst;
bufferSize = bufferIncrement;
buffer = malloc(bufferSize);
if(!buffer)
return S_FALSE;
Status = RegQueryValueExA(hKey, name, NULL, &type, buffer, &bufferSize);
while(Status == ERROR_MORE_DATA)
{
bufferSize += bufferIncrement;
buffer = realloc(buffer, bufferSize);
if(!buffer)
return S_FALSE;
Status = RegQueryValueExA(hKey, name, NULL, &type, buffer, &bufferSize);
}
src = buffer;
while(*src)
{
if(!strcmp(src, append))
{
isExist = TRUE;
break;
}
src += strlen(src) + 1;
}
if(!isExist)
{
int appendLen = strlen(append);
LPBYTE newBuffer = malloc(bufferSize + appendLen + 1);
Status = S_FALSE;
if(newBuffer)
{
src = buffer;
dst = (PCHAR)newBuffer;
while(*src)
{
int len = strlen(src) + 1;
strcpy(dst, src);
src += len;
dst += len;
}
strcpy(dst, append);
dst += appendLen + 1;
*dst = 0;
Status = RegSetValueExA(hKey, name, 0, REG_MULTI_SZ, newBuffer, bufferSize + appendLen + 1);
free(newBuffer);
}
}
free(buffer);
RegCloseKey(hKey);
}
return Status;
}
LSTATUS CreateRegKey(HKEY key, LPCSTR subKey)
{
HKEY hKey;
LSTATUS Status;
REGSAM sam = KEY_ALL_ACCESS;
if(Is64BitWindows && RegWow64)
sam |= KEY_WOW64_64KEY;
Status = RegCreateKeyExA(key, subKey, 0, NULL, 0, sam, NULL, &hKey, NULL);
if(Status == ERROR_SUCCESS)
{
RegCloseKey(hKey);
}
return Status;
}
LSTATUS DeleteRegKey(HKEY key, LPCSTR subKey, LPCSTR name)
{
HKEY hKey;
LSTATUS Status;
REGSAM sam = KEY_ALL_ACCESS;
if(Is64BitWindows && RegWow64)
sam |= KEY_WOW64_64KEY;
Status = RegOpenKeyExA(key, subKey, 0, sam, &hKey);
if(Status == ERROR_SUCCESS)
{
Status = RegDeleteKeyA(hKey, name);
RegCloseKey(hKey);
}
return Status;
}
LSTATUS DeleteRegValue(HKEY key, LPCSTR subKey, LPCSTR name)
{
HKEY hKey;
LSTATUS Status;
REGSAM sam = KEY_ALL_ACCESS;
if(Is64BitWindows && RegWow64)
sam |= KEY_WOW64_64KEY;
Status = RegOpenKeyExA(key, subKey, 0, sam, &hKey);
if(Status == ERROR_SUCCESS)
{
Status = RegDeleteValueA(hKey, name);
RegCloseKey(hKey);
}
return Status;
}
//////////////////////////////////////////////////////////////////////////
BOOL InstallNdisFilter(LPCSTR serviceName, LPCSTR serviceDesc, LPCSTR sysPath, LPCSTR netCfgInstanceId)
{
LPCSTR sysFile;
PVOID OldRedir;
CHAR Path[256];
BOOL bRet;
//復(fù)制驅(qū)動程序文件
ShutdownWow64Redir(&OldRedir);
sysFile = strrchr(sysPath, '\\');
if(!sysFile)
sysFile = sysPath;
ExpandEnvironmentStrings("%systemroot%\\system32\\drivers\\", Path, sizeof(Path));
strcat(Path, sysFile);
bRet = CopyFile(sysPath, Path, FALSE);
RevertWow64Redir(&OldRedir);
if(!bRet)
{
printf("Copy driver file %s failed\n", sysFile);
return FALSE;
}
//創(chuàng)建驅(qū)動服務(wù)
sprintf(Path, "\\SystemRoot\\System32\\drivers\\%s", sysFile);
bRet = _CreateService(serviceName, serviceDesc, Path, TRUE, TRUE, "NDIS");
if(!bRet)
{
printf("Create service %s failed\n", serviceName);
return FALSE;
}
//NDIS Version
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s", serviceName);
SetRegDWORD(HKEY_LOCAL_MACHINE, Path, "NdisMajorVersion", 6);
SetRegDWORD(HKEY_LOCAL_MACHINE, Path, "NdisMinorVersion", 0);
//INF Common.Params.reg
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\FilterAdapterParams", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\FilterAdapterParams\\AdapterParam", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
SetRegString(HKEY_LOCAL_MACHINE, Path, "ParamDesc", "Adapterparam for lwf");
SetRegString(HKEY_LOCAL_MACHINE, Path, "type", "int");
SetRegString(HKEY_LOCAL_MACHINE, Path, "default", "10");
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\FilterDriverParams", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\FilterDriverParams\\DriverParam", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
SetRegString(HKEY_LOCAL_MACHINE, Path, "ParamDesc", "Driverparam for lwf");
SetRegString(HKEY_LOCAL_MACHINE, Path, "type", "int");
SetRegString(HKEY_LOCAL_MACHINE, Path, "default", "5");
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\Parameters", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
SetRegString(HKEY_LOCAL_MACHINE, Path, "DriverParam", "5");
SetRegDWORD(HKEY_LOCAL_MACHINE, Path, "DefaultFilterSettings", 1);
//Binding
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\Parameters\\Adapters", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
sprintf(Path, "SYSTEM\\CurrentControlSet\\services\\%s\\Parameters\\NdisAdapters", serviceName);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
//INF Ndi part, ignore: InfPath InfSection InstallTimeStamp LocDescription
sprintf(Path, "SYSTEM\\CurrentControlSet\\Control\\Network\\{4d36e974-e325-11ce-bfc1-08002be10318}\\%s", netCfgInstanceId);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
SetRegDWORD(HKEY_LOCAL_MACHINE, Path, "Characteristics", NCF_LW_FILTER);
SetRegString(HKEY_LOCAL_MACHINE, Path, "ComponentId", serviceName);
SetRegString(HKEY_LOCAL_MACHINE, Path, "Description", serviceDesc);
//INF Ndi part, ignore: TimeStamp
sprintf(Path, "SYSTEM\\CurrentControlSet\\Control\\Network\\{4d36e974-e325-11ce-bfc1-08002be10318}\\%s\\Ndi", netCfgInstanceId);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
SetRegMultiString1(HKEY_LOCAL_MACHINE, Path, "CoServices", serviceName);
SetRegString(HKEY_LOCAL_MACHINE, Path, "FilterClass", "compression");
SetRegDWORD(HKEY_LOCAL_MACHINE, Path, "FilterRunType", 1);
SetRegDWORD(HKEY_LOCAL_MACHINE, Path, "FilterType", 2);
SetRegString(HKEY_LOCAL_MACHINE, Path, "HelpText", serviceDesc);
SetRegMultiString1(HKEY_LOCAL_MACHINE, Path, "Services", serviceName);
//INF Ndi Part
sprintf(Path, "SYSTEM\\CurrentControlSet\\Control\\Network\\{4d36e974-e325-11ce-bfc1-08002be10318}\\%s\\Ndi\\Interfaces", netCfgInstanceId);
CreateRegKey(HKEY_LOCAL_MACHINE, Path);
SetRegString(HKEY_LOCAL_MACHINE, Path, "FilterMediaTypes", "ethernet");
SetRegString(HKEY_LOCAL_MACHINE, Path, "LowerRange", "nolower");
SetRegString(HKEY_LOCAL_MACHINE, Path, "UpperRange", "noupper");
return TRUE;
}
void RestartDevice(LPCSTR PnpInstanceId)
{
HDEVINFO hDevInfo = NULL;
do {
DWORD Index;
hDevInfo = SetupDiGetClassDevs(NULL,NULL,NULL, DIGCF_PRESENT | DIGCF_ALLCLASSES);
if(!hDevInfo)
break;
Index = 0;
while(1)
{
SP_DEVINFO_DATA sdd = {sizeof(sdd)};
char instanceId[256];
if(!SetupDiEnumDeviceInfo(hDevInfo, Index++, &sdd))
break;
if(SetupDiGetDeviceInstanceId(hDevInfo, &sdd, instanceId, sizeof(instanceId), NULL))
{
if(!strcmp(instanceId, PnpInstanceId))
{
SP_PROPCHANGE_PARAMS params = {sizeof(SP_CLASSINSTALL_HEADER)};
params.ClassInstallHeader.InstallFunction = DIF_PROPERTYCHANGE;
params.Scope = DICS_FLAG_CONFIGSPECIFIC;
params.HwProfile = 0;
params.StateChange = DICS_DISABLE;
SetupDiSetClassInstallParams(hDevInfo, &sdd, ¶ms.ClassInstallHeader, sizeof(params));
SetupDiChangeState(hDevInfo, &sdd);
params.StateChange = DICS_ENABLE;
SetupDiSetClassInstallParams(hDevInfo, &sdd, ¶ms.ClassInstallHeader, sizeof(params));
SetupDiChangeState(hDevInfo, &sdd);
break;
}
}
}
} while (0);
if(hDevInfo)
SetupDiDestroyDeviceInfoList(hDevInfo);
}
BOOL InstallNdisFilterBind(LPCSTR filterServiceName, LPCSTR filterNetCfgInstanceId)
{
LPCSTR enumPath;
HKEY hKey;
DWORD sam = KEY_READ, index = 0;
LSTATUS Status;
//枚舉所有 ethernet 網(wǎng)卡闲延,并添加綁定豹缀。用 GetIfTable2 也可,我這里使用注冊表遍歷慨代。
enumPath = "SYSTEM\\CurrentControlSet\\Control\\Class\\{4D36E972-E325-11CE-BFC1-08002BE10318}";
Status = RegOpenKeyExA(HKEY_LOCAL_MACHINE, enumPath, 0, sam, &hKey);
if(Status != S_OK)
return FALSE;
while(1)
{
CHAR name[256], path[256], netCfgInstanceId[128];
DWORD nameSize = sizeof(name);
DWORD ifType, ifChar, ifLuid;
if(RegEnumKeyExA(hKey, index++, name, &nameSize, NULL, NULL, NULL, NULL) != S_OK)
break;
sprintf(path, "%s\\%s", enumPath, name);
if(QueryRegString(HKEY_LOCAL_MACHINE, path, "NetCfgInstanceId", netCfgInstanceId, sizeof(netCfgInstanceId)) != S_OK)
continue;
if(QueryRegDWORD(HKEY_LOCAL_MACHINE, path, "*IfType", &ifType) != S_OK)
continue;
if(QueryRegDWORD(HKEY_LOCAL_MACHINE, path, "NetLuidIndex", &ifLuid) != S_OK)
continue;
if(QueryRegDWORD(HKEY_LOCAL_MACHINE, path, "Characteristics", &ifChar) != S_OK)
continue;
if( (ifType == MIB_IF_TYPE_ETHERNET || ifType == IF_TYPE_IEEE80211) && //是以太網(wǎng)或WiFi適配器
!(ifChar & NCF_VIRTUAL) ) //不是虛擬適配器
{
//綁定到 NdisFilter
CHAR bindItem[256], pnpInstanceId[256];
NET_LUID Luid;
GUID Guid;
sprintf(bindItem, "%s-%s-0000", netCfgInstanceId, filterNetCfgInstanceId);
printf("Bind to %s\n", filterNetCfgInstanceId);
sprintf(path, "%s\\%s\\Linkage", enumPath, name);
printf("Append FilterList %s\n", bindItem);
AppendRegMultiString(HKEY_LOCAL_MACHINE, path, "FilterList", bindItem);
//Binding
sprintf(path, "SYSTEM\\CurrentControlSet\\services\\%s\\Parameters\\Adapters\\%s", filterServiceName, netCfgInstanceId);
CreateRegKey(HKEY_LOCAL_MACHINE, path);
sprintf(path, "SYSTEM\\CurrentControlSet\\services\\%s\\Parameters\\Adapters\\%s\\%s-0000", filterServiceName, netCfgInstanceId, filterNetCfgInstanceId);
CreateRegKey(HKEY_LOCAL_MACHINE, path);
sprintf(path, "SYSTEM\\CurrentControlSet\\services\\%s\\Parameters\\NdisAdapters\\%s", filterServiceName, netCfgInstanceId);
CreateRegKey(HKEY_LOCAL_MACHINE, path);
SetRegString(HKEY_LOCAL_MACHINE, path, "AdapterParam", "10");
memset(&Guid, 0, sizeof(Guid));
Luid.Info.Reserved = 0;
Luid.Info.IfType = ifType;
Luid.Info.NetLuidIndex = ifLuid;
ConvertInterfaceLuidToGuid(&Luid, &Guid);
SetRegValue(HKEY_LOCAL_MACHINE, path, "InterfaceGuid", (LPCBYTE)&Guid, sizeof(Guid), REG_BINARY);
//禁用啟用網(wǎng)卡
sprintf(path, "SYSTEM\\CurrentControlSet\\Control\\Network\\{4D36E972-E325-11CE-BFC1-08002BE10318}\\%s\\Connection", netCfgInstanceId);
QueryRegString(HKEY_LOCAL_MACHINE, path, "PnPInstanceId", pnpInstanceId, sizeof(pnpInstanceId));
printf("Restart %s pnpId %s\n", netCfgInstanceId, pnpInstanceId);
RestartDevice(pnpInstanceId);
}
}
RegCloseKey(hKey);
return TRUE;
}
int main(int argc, char *argv[])
{
char *SysPath;
char *NetCfgInstanceId;
//獲取操作系統(tǒng)版本
GetOsVer();
//設(shè)定過濾驅(qū)動程序路徑和實例GUID
if(Is64BitWindows)
SysPath = "tcpmasq64.sys";
else
SysPath = "tcpmasq32.sys";
NetCfgInstanceId = "{91E009E2-A9A3-42B7-9E22-3A1D389D7D4D}";
//安裝過濾驅(qū)動服務(wù)
printf("Install NDIS Filter\n");
InstallNdisFilter("tcpmasq", "TcpMasq NT6 LWF Driver", SysPath, NetCfgInstanceId);
//添加綁定的網(wǎng)卡
printf("NDIS Filter Bind\n");
InstallNdisFilterBind("tcpmasq", NetCfgInstanceId);
//BUG: 在控制面板重新禁用啟用網(wǎng)卡邢笙,會丟掉 Bind
//可能是由于 HKLM\SYSTEM\CurrentControlSet\Control\Network\Config 數(shù)據(jù)里面沒有剛注冊的 NDIS Filter
//Config 讀寫位于 netcfgx.dll
//關(guān)鍵字 WRITING CONFIG BLOB 日志寫入 C:\Windows\inf\setupapi.dev.log
//FIXME
return 0;
}