C/C++實現(xiàn)枚舉網(wǎng)上鄰居信息的示例詳解
在Windows系統(tǒng)中,通過網(wǎng)絡(luò)鄰居可以方便地查看本地網(wǎng)絡(luò)中的共享資源和計算機。通過使用Windows API中的一些網(wǎng)絡(luò)相關(guān)函數(shù),我們可以實現(xiàn)枚舉網(wǎng)絡(luò)鄰居信息的功能,獲取連接到本地網(wǎng)絡(luò)的其他計算機的相關(guān)信息。本文將介紹一個簡單的C++程序,使用Windows API枚舉網(wǎng)絡(luò)鄰居信息,并獲取對端名稱、本機名稱、主機名稱以及主機IP等信息。
引言
首先,我們需要了解一下幾個與網(wǎng)絡(luò)鄰居信息有關(guān)的Windows API函數(shù):
NETRESOURCE 結(jié)構(gòu)體是 Windows 網(wǎng)絡(luò) API 中的一個結(jié)構(gòu)體,用于描述網(wǎng)絡(luò)資源的信息。它在網(wǎng)絡(luò)資源的枚舉和連接等操作中經(jīng)常被使用。
結(jié)構(gòu)體定義
typedef struct _NETRESOURCE {
DWORD dwScope;
DWORD dwType;
DWORD dwDisplayType;
DWORD dwUsage;
LPTSTR lpLocalName;
LPTSTR lpRemoteName;
LPTSTR lpComment;
LPTSTR lpProvider;
} NETRESOURCE, *LPNETRESOURCE;
結(jié)構(gòu)體成員
dwScope:指定資源的可見性??赡艿娜≈禐椋?RESOURCE_CONNECTED:表示已連接的資源。RESOURCE_CONTEXT:表示會話特定的資源。
dwType:指定資源的類型??赡艿娜≈禐椋?ul>RESOURCETYPE_ANY:表示任何類型的資源。RESOURCETYPE_DISK:表示磁盤資源。RESOURCETYPE_PRINT:表示打印機資源。
dwDisplayType:指定資源的顯示類型??赡艿娜≈禐椋?ul>RESOURCEDISPLAYTYPE_GENERIC:表示通用資源。RESOURCEDISPLAYTYPE_DOMAIN:表示域。dwUsage:指定資源的使用類型??赡艿娜≈禐椋?ul>RESOURCEUSAGE_CONNECTABLE:表示資源可以連接。RESOURCEUSAGE_CONTAINER:表示資源是一個容器,可以包含其他資源。lpLocalName:指定本地驅(qū)動器或打印機的本地名稱。lpRemoteName:指定遠程共享資源的網(wǎng)絡(luò)名稱。lpComment:指定資源的注釋。lpProvider:指定提供資源的網(wǎng)絡(luò)提供程序的名稱。WNetOpenEnum 是 Windows 網(wǎng)絡(luò)功能中的一個API函數(shù),WNetOpenEnum 通過指定的參數(shù)打開一個用于列舉網(wǎng)絡(luò)資源的枚舉句柄。這個句柄可以在后續(xù)的操作中用于獲取網(wǎng)絡(luò)資源的枚舉信息。
函數(shù)原型
DWORD WNetOpenEnum( DWORD dwScope, DWORD dwType, DWORD dwUsage, LPNETRESOURCE lpNetResource, LPHANDLE lphEnum );
參數(shù)說明
dwScope:指定枚舉的范圍,可以是RESOURCE_CONNECTED、RESOURCE_GLOBALNET、RESOURCE_REMEMBERED、RESOURCE_CONTEXT中的一個。dwType:指定枚舉資源的類型,可以是RESOURCETYPE_DISK、RESOURCETYPE_PRINT、RESOURCETYPE_ANY中的一個。dwUsage:指定枚舉資源的使用類型,可以是RESOURCEUSAGE_CONNECTABLE、RESOURCEUSAGE_CONTAINER、RESOURCEUSAGE_NOLOCALDEVICE、RESOURCEUSAGE_SIBLING中的一個。lpNetResource:指向NETRESOURCE結(jié)構(gòu)的指針,用于指定枚舉的起始位置。如果為NULL,則從所有資源的最頂層開始枚舉。lphEnum:指向句柄的指針,用于接收枚舉句柄。
返回值
如果函數(shù)調(diào)用成功,返回 NO_ERROR,否則返回一個錯誤代碼,可以通過 GetLastError 函數(shù)獲取詳細信息。
WNetEnumResource 是 Windows 網(wǎng)絡(luò)功能中的 API 函數(shù)之一,用于通過枚舉句柄獲取網(wǎng)絡(luò)資源的詳細信息,包括資源的類型、用途、本地名、遠程名等信息。
函數(shù)原型
DWORD WNetEnumResource( HANDLE hEnum, LPDWORD lpcCount, LPVOID lpBuffer, LPDWORD lpBufferSize );
參數(shù)說明
hEnum:枚舉句柄,通過WNetOpenEnum函數(shù)獲取的句柄。lpcCount:指向一個變量的指針,該變量用于接收枚舉的資源數(shù)目。lpBuffer:指向一個緩沖區(qū)的指針,用于接收枚舉的資源信息。lpBufferSize:指向一個變量的指針,該變量用于指定或接收緩沖區(qū)的大小。
返回值
如果函數(shù)調(diào)用成功,返回 NO_ERROR,否則返回一個錯誤代碼,可以通過 GetLastError 函數(shù)獲取詳細信息。
WNetCloseEnum 函數(shù)用于關(guān)閉由 WNetOpenEnum 函數(shù)打開的網(wǎng)絡(luò)資源的枚舉句柄。在使用 WNetOpenEnum 函數(shù)枚舉網(wǎng)絡(luò)資源后,當(dāng)不再需要使用枚舉句柄時,應(yīng)該通過調(diào)用 WNetCloseEnum 函數(shù)來釋放資源,避免內(nèi)存泄漏。
函數(shù)定義
DWORD WNetCloseEnum( HANDLE hEnum );
參數(shù)
hEnum:網(wǎng)絡(luò)資源的枚舉句柄,該句柄是由WNetOpenEnum函數(shù)返回的。
返回值
如果函數(shù)調(diào)用成功,返回 NO_ERROR,否則返回錯誤代碼,可以通過 GetLastError 函數(shù)獲取詳細的錯誤信息。
代碼實現(xiàn)
以下是一個簡單的C++程序,使用上述API函數(shù)實現(xiàn)了枚舉網(wǎng)絡(luò)鄰居信息的功能。該程序通過遍歷枚舉得到的網(wǎng)絡(luò)資源信息,獲取對端名稱、本機名稱、主機名稱以及主機IP等信息,并輸出到控制臺。
#include <iostream>
#include <Windows.h>
#include <winnetwk.h>
#pragma comment(lib,"Mpr.lib")
#pragma comment(lib,"Ws2_32.lib")
// 枚舉網(wǎng)絡(luò)鄰居
BOOL EnumNetResource()
{
NETRESOURCE *NetResource = NULL;
HANDLE hEnum;
unsigned int i;
char szHostName[MAX_PATH] = { 0 };
hostent *host = NULL;
char *lpszIP = NULL;
// 通過WSAStartup函數(shù)完成對Winsock服務(wù)的初始化
WSADATA wsaData = { 0 };
WSAStartup(MAKEWORD(2, 2), &wsaData);
// 指定枚舉范圍, 獲取枚舉句柄
WNetOpenEnum(RESOURCE_CONTEXT, NULL, NULL, NULL, &hEnum);
if (hEnum)
{
DWORD Count = 0xFFFFFFFF;
DWORD BufferSize = 2048;
BYTE *pBuffer = new BYTE[2048];
// 根據(jù)設(shè)置的枚舉返回, 獲取枚舉信息
WNetEnumResource(hEnum, &Count, pBuffer, &BufferSize);
NetResource = (NETRESOURCE*)pBuffer;
for (i = 0; i < BufferSize / sizeof(NETRESOURCE); i++, NetResource++)
{
// 判斷資源類型是否是所有資源 以及 判斷資源使用類型是否是容器資源
if (NetResource->dwUsage == RESOURCEUSAGE_CONTAINER && NetResource->dwType == RESOURCETYPE_ANY)
{
if (NetResource->lpRemoteName)
{
// 獲取遠程主機名
RtlZeroMemory(szHostName, MAX_PATH);
lstrcpy(szHostName, (char *)((DWORD64)NetResource->lpRemoteName + 2));
// 根據(jù)主機名獲取IP地址信息
host = gethostbyname(szHostName);
if (host == NULL)
{
std::cout << "錯誤代碼" << std::endl;
continue;
}
// 將Ipv4網(wǎng)絡(luò)地址轉(zhuǎn)換為Internet標(biāo)準(zhǔn)點分十進制格式的ASCII字符串
lpszIP = inet_ntoa(*(in_addr *)host->h_addr_list[0]);
std::cout << "對端名稱: " << NetResource->lpRemoteName
<< " 本機名稱: " << NetResource->lpLocalName
<< " 主機名稱: " << szHostName
<< " 主機IP: " << lpszIP
<< std::endl;
}
}
}
// 釋放內(nèi)存并關(guān)閉句柄
delete[]pBuffer;
pBuffer = NULL;
WNetCloseEnum(hEnum);
}
return TRUE;
}
int main(int argc, char *argv[])
{
EnumNetResource();
system("pause");
return 0;
}
結(jié)語
通過這個簡單的程序,我們可以了解如何使用Windows API函數(shù)來枚舉網(wǎng)絡(luò)鄰居信息。這對于需要在程序中獲取網(wǎng)絡(luò)中其他計算機信息的場景是非常有用的。在實際應(yīng)用中,可以根據(jù)需要進一步擴展和優(yōu)化代碼,以滿足特定的功能需求。
以上就是C/C++實現(xiàn)枚舉網(wǎng)上鄰居信息的示例詳解的詳細內(nèi)容,更多關(guān)于C/C++枚舉網(wǎng)上鄰居信息的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Linux下實現(xiàn)C++操作Mysql數(shù)據(jù)庫
由于工作需要抽出一周的時間來研究C/C++訪問各種數(shù)據(jù)庫的方法,并打算封裝一套數(shù)據(jù)庫操作類,現(xiàn)在奉上最簡單的一部分:在Linux下訪問MySQL數(shù)據(jù)庫。2017-05-05
詳解C標(biāo)準(zhǔn)庫堆內(nèi)存函數(shù)
在C/C++語言中,我們知道內(nèi)存分為這幾種:程序全局變量內(nèi)存、棧內(nèi)存、堆內(nèi)存。其中堆內(nèi)存就是通過malloc(new)來分配的內(nèi)存,本文我們來探討一下C標(biāo)準(zhǔn)庫堆內(nèi)存函數(shù)。2021-06-06
C++簡明圖解分析靜態(tài)成員與單例設(shè)計模式
與靜態(tài)數(shù)據(jù)成員不同,靜態(tài)成員函數(shù)的作用不是為了對象之間的溝通,而是為了能處理靜態(tài)數(shù)據(jù)成員,靜態(tài)成員函數(shù)沒有this指針。既然它沒有指向某一對象,也就無法對一個對象中的非靜態(tài)成員進行默認訪問2022-06-06

