delphi版不重启改ip、网关、dns
本帖最后由 9908006 于 2010-12-3 22:42 编辑翻译自vc
program MASK;
uses
windows, SysUtils;
const
MAX_ADAPTER_NAME_LENGTH = 256;
MAX_ADAPTER_DESCRIPTION_LENGTH = 128;
MAX_ADAPTER_ADDRESS_LENGTH = 8;
IPHelper = 'iphlpapi.dll';
type
USHORT = WORD;
ULONG = DWORD;
time_t = Longint;
IP_ADDRESS_STRING = record
S: array of Char;
end;
IP_MASK_STRING = IP_ADDRESS_STRING;
PIP_MASK_STRING = ^IP_MASK_STRING;
PIP_ADDR_STRING = ^IP_ADDR_STRING;
IP_ADDR_STRING = record
Next: PIP_ADDR_STRING;
IpAddress: IP_ADDRESS_STRING;
IpMask: IP_MASK_STRING;
Context: DWORD;
end;
PIP_ADAPTER_INFO = ^IP_ADAPTER_INFO;
IP_ADAPTER_INFO = record
Next: PIP_ADAPTER_INFO;
ComboIndex: DWORD;
AdapterName: array of Char;
Description: array of Char;
AddressLength: UINT;
Address: array of BYTE;
Index: DWORD;
Type_: UINT;
DhcpEnabled: UINT;
CurrentIpAddress: PIP_ADDR_STRING;
IpAddressList: IP_ADDR_STRING;
GatewayList: IP_ADDR_STRING;
DhcpServer: IP_ADDR_STRING;
HaveWins: BOOL;
PrimaryWinsServer: IP_ADDR_STRING;
SecondaryWinsServer: IP_ADDR_STRING;
LeaseObtained: time_t;
LeaseExpires: time_t;
end;
function GetAdaptersInfo(pAdapterInfo: PIP_ADAPTER_INFO; var pOutBufLen: ULONG): DWORD; stdcall; external IPHelper;
function StringToWideString(const S: string): WideString;
var
InputLength, OutputLength: Integer;
begin
InputLength := Length(S);
OutputLength := MultiByteToWideChar(CP_ACP, 0, PChar(S), InputLength, nil, 0);
SetLength(Result, OutputLength);
MultiByteToWideChar(CP_ACP, 0, PChar(S), InputLength, PWideChar(Result), OutputLength);
end;
function NotifyIPChange(lpszAdapterName: string): bool;
type TDhcpNotifyConfigChange = function(lpwszServerName: PWideChar; // 本地机器为NULL
lpwszAdapterName: PWideChar; // 适配器名称
bNewIpAddress: BOOL; // TRUE表示更改IP
dwIpIndex: DWORD; // 指明第几个IP地址,如果只有该接口只有一个IP地址则为0
dwIpAddress: DWORD; // IP地址
dwSubNetMask: DWORD; // 子网掩码
nDhcpAction: Integer): BOOL; stdcall;
var
hDhcpDll: dword;
MyDhcpNotifyConfigChange: TDhcpNotifyConfigChange;
begin
hDhcpDll := LoadLibrary('dhcpcsvc.dll');
if hDhcpDll <> 0 then
begin
MyDhcpNotifyConfigChange := GetProcAddress(hDhcpDll, 'DhcpNotifyConfigChange');
MyDhcpNotifyConfigChange(nil, pwidechar(StringToWideString(lpszAdapterName)), FALSE, 0, 0, 0, 0)
end;
CloseHandle(hDhcpDll);
end;
function RegIp(lpszAdapterName, pIPAddress, pNetMask, pNetGate, pDNSServer1, pDNSServer2: string): bool;
var
hkRoot: HKEY;
mszDNSServer, mszIPAddress, mszNetMask, mszNetGate: string;
strKeyName: string;
begin
strKeyName := 'SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\Interfaces\' + lpszAdapterName;
if (RegOpenKeyEx(HKEY_LOCAL_MACHINE, pchar(strKeyName), 0, KEY_WRITE, hkRoot) <> ERROR_SUCCESS)
then exit;
mszDNSServer := pDNSServer1 + ',' + pDNSServer2;
mszIPAddress := pIPAddress + #0#0;
mszNetMask := pNetMask + #0#0;
mszNetGate := pNetGate + #0#0;
RegSetValueEx(hkRoot, 'IPAddress', 0, REG_MULTI_SZ, pchar(mszIPAddress), length(mszIPAddress));
RegSetValueEx(hkRoot, 'SubnetMask', 0, REG_MULTI_SZ, pchar(mszNetMask), length(mszNetMask));
RegSetValueEx(hkRoot, 'DefaultGateway', 0, REG_MULTI_SZ, pchar(mszNetGate), length(mszNetGate));
RegSetValueEx(hkRoot, 'NameServer', 0, REG_SZ, pchar(mszDNSServer), length(mszDNSServer));
RegCloseKey(hkRoot);
end;
function GetLanAdapterName: string;
var
InterfaceInfo, TmpPointer: PIP_ADAPTER_INFO;
IP: PIP_ADDR_STRING;
Len: ULONG;
begin
result := '';
if GetAdaptersInfo(nil, Len) = ERROR_BUFFER_OVERFLOW then
begin
GetMem(InterfaceInfo, Len);
try
if GetAdaptersInfo(InterfaceInfo, Len) = ERROR_SUCCESS then
begin
TmpPointer := InterfaceInfo;
result := TmpPointer.AdapterName;
end;
finally
FreeMem(InterfaceInfo);
end;
end;
end;
var
AdapterName: string;
begin
AdapterName := GetLanAdapterName;
RegIp(AdapterName, '192.168.0.5', '255.255.255.0', 11.10.10.1', 111.111.11.111', '111.111.11.112');
NotifyIPChange(AdapterName);
end.
如果是C语言版就好了。。。 如你所愿,有个类似的vc代码
//VC-ConsoleWithApi
#include <windows.h>
#include <string>
#include <iostream>
#pragma comment(lib,"Ws2_32.lib")
using namespace std;
void GetLanAdapterName( char* szLanAdapterName );
BOOL RegIP( LPCTSTR lpszAdapterName, LPCTSTR pIPAddress, LPCTSTR pNetMask, LPCTSTR pNetGate,LPCTSTR pDNSServer1,LPCTSTR pDNSServer2 );
BOOL NotifyIPChange( LPCTSTR lpszAdapterName, int nIndex, LPCTSTR pIPAddress, LPCTSTR pNetMask );
int main()
{
char AdapterName[ MAX_PATH ] ="";
GetLanAdapterName( AdapterName );
// MessageBox(0,AdapterName ,"ff",0);
RegIP( AdapterName, "172.20.10.253","255.255.255.0", "172.20.10.1", "211.136.17.107", "211.136.18.171" );
NotifyIPChange( AdapterName, 0, "172.20.10.253","172.20.10.1" );
return 0;
}
//读取注册表取得适配器名称
void GetLanAdapterName(char* szLanAdapterName)
{
HKEY hKey, hSubKey, hNdiIntKey;
if( ::RegOpenKeyEx( HKEY_LOCAL_MACHINE, "System\\CurrentControlSet\\Control\\Class\\{4D36E972-E325-11CE-BFC1-08002BE10318}", 0, KEY_READ, &hKey ) != ERROR_SUCCESS )
return;
DWORD dwIndex = 0;
DWORD dwBufSize = 256;
DWORD dwDataType;
char szSubKey;
unsigned char szData;
while( ::RegEnumKeyEx( hKey, dwIndex++, szSubKey, &dwBufSize, NULL, NULL, NULL, NULL ) == ERROR_SUCCESS )
{
if( ::RegOpenKeyEx( hKey, szSubKey, 0, KEY_READ, &hSubKey ) == ERROR_SUCCESS )
{
if( ::RegOpenKeyEx( hSubKey, "Ndi\\Interfaces", 0, KEY_READ, &hNdiIntKey ) == ERROR_SUCCESS )
{
dwBufSize = 256;
if( ::RegQueryValueEx( hNdiIntKey, "LowerRange", 0, &dwDataType, szData, &dwBufSize ) == ERROR_SUCCESS )
{
if( strcmp( (char*)szData, "ethernet" ) == 0 ) // 判断是不是以太网卡
{
dwBufSize = 256;
if( ::RegQueryValueEx( hSubKey, "DriverDesc", 0, &dwDataType, szData, &dwBufSize ) == ERROR_SUCCESS )
{
// szData 中便是适配器详细描述
dwBufSize = 256;
if( ::RegQueryValueEx( hSubKey, "NetCfgInstanceID", 0, &dwDataType, szData, &dwBufSize ) == ERROR_SUCCESS )
{
//szData中便是适配器名称
strcpy( szLanAdapterName, (const char *)szData );
break;
}
}
}
}
::RegCloseKey( hNdiIntKey );
}
::RegCloseKey(hSubKey);
}
dwBufSize = 256;
}
/* end of while */
::RegCloseKey(hKey);
}
BOOL RegIP( LPCTSTR lpszAdapterName, LPCTSTR pIPAddress, LPCTSTR pNetMask, LPCTSTR pNetGate,LPCTSTR pDNSServer1,LPCTSTR pDNSServer2 )
{
HKEY hKey;
string strKeyName = "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters\\Interfaces\\";
strKeyName += lpszAdapterName;
if( ::RegOpenKeyEx( HKEY_LOCAL_MACHINE, strKeyName.c_str(), 0, KEY_WRITE, &hKey ) != ERROR_SUCCESS )
return FALSE;
string DNSServer = pDNSServer1;
DNSServer += ",";
DNSServer += pDNSServer2;
char mszIPAddress[ 100 ];
char mszNetMask[ 100 ];
char mszNetGate[ 100 ];
char mszDNSServer[ 100 ];
strncpy( mszIPAddress, pIPAddress, 98 );
strncpy( mszNetMask, pNetMask, 98 );
strncpy( mszNetGate, pNetGate, 98 );
strncpy( mszDNSServer, DNSServer.c_str(), 98 );
int nIP, nMask, nGate, nDNSServer;
nIP = strlen( mszIPAddress );
nMask = strlen( mszNetMask );
nGate = strlen( mszNetGate );
nDNSServer = strlen( mszDNSServer );
*( mszIPAddress + nIP + 1 ) = 0x00; // REG_MULTI_SZ数据需要在后面再加个0
nIP += 2;
*( mszNetMask + nMask + 1 ) = 0x00;
nMask += 2;
*( mszNetGate + nGate + 1 ) = 0x00;
nGate += 2;
*( mszDNSServer + nDNSServer + 1 ) = 0x00;
nGate += 2;
::RegSetValueEx( hKey, "IPAddress", 0, REG_MULTI_SZ, (unsigned char*)mszIPAddress, nIP );
::RegSetValueEx( hKey, "SubnetMask", 0, REG_MULTI_SZ, (unsigned char*)mszNetMask, nMask );
::RegSetValueEx( hKey, "DefaultGateway", 0, REG_MULTI_SZ, (unsigned char*)mszNetGate, nGate );
::RegSetValueEx( hKey, "NameServer", 0, REG_SZ, (unsigned char*)mszDNSServer, nDNSServer );
::RegCloseKey(hKey);
return TRUE;
}
//未公开函数DhcpNotifyConfigChange位于 dhcpcsvc.dll中.
//原型声明
typedef BOOL ( CALLBACK* DHCPNOTIFYPROC) (
LPWSTR lpwszServerName, // 本地机器为NULL
LPWSTR lpwszAdapterName, // 适配器名称
BOOL bNewIpAddress, // TRUE表示更改IP
DWORD dwIpIndex, // 指明第几个IP地址,如果只有该接口只有一个IP地址则为0
DWORD dwIpAddress, // IP地址
DWORD dwSubNetMask, // 子网掩码
int nDhcpAction // 对DHCP的操作 0:不修改, 1:启用 DHCP,2:禁用 DHCP
);
BOOL NotifyIPChange( LPCTSTR lpszAdapterName, int nIndex, LPCTSTR pIPAddress, LPCTSTR pNetMask )
{
BOOL bResult = FALSE;
HINSTANCE hDhcpDll;
DHCPNOTIFYPROC pDhcpNotifyProc;
WCHAR wcAdapterName;
MultiByteToWideChar( CP_ACP, 0, lpszAdapterName, -1, wcAdapterName,256 );
if( ( hDhcpDll = ::LoadLibrary("dhcpcsvc.dll") ) == NULL )
return FALSE;
if( ( pDhcpNotifyProc = (DHCPNOTIFYPROC)::GetProcAddress( hDhcpDll, "DhcpNotifyConfigChange" ) ) != NULL )
if((pDhcpNotifyProc)(NULL, wcAdapterName, TRUE, nIndex, inet_addr(pIPAddress), inet_addr(pNetMask), 0 ) == ERROR_SUCCESS )
bResult = TRUE;
::FreeLibrary(hDhcpDll);
return bResult;
} C代码比pascal代码顺眼多了。。。 ......我看着都蛋疼:Q 精品文章必须顶 测试一下,看好用吗 好帖子,学习了!
页:
[1]