
Introduction
This sample snippet shows how to retrieve the list of all network adapters on your machine, plus a lot of infos about each of them. The information you can retrieve are all the members of the structure MIB_IFROW as shown in this MSDN snippet
typedef struct _MIB_IFROW {
WCHAR wszName[MAX_INTERFACE_NAME_LEN];
DWORD dwIndex; DWORD dwType; DWORD dwMtu; DWORD dwSpeed; DWORD dwPhysAddrLen; BYTE bPhysAddr[MAXLEN_PHYSADDR]; DWORD dwAdminStatus; DWORD dwOperStatus; DWORD dwLastChange; DWORD dwInOctets; DWORD dwInUcastPkts; DWORD dwInNUcastPkts; DWORD dwInDiscards; DWORD dwInErrors; DWORD dwInUnknownProtos; DWORD dwOutOctets; DWORD dwOutUcastPkts; DWORD dwOutNUcastPkts; DWORD dwOutDiscards; DWORD dwOutErrors; DWORD dwOutQLen; DWORD dwDescrLen; BYTE bDescr[MAXLEN_IFDESCR]; } MIB_IFROW,*PMIB_IFROW;After wasted lot of time trying to reach the performance counter stuff I found this DLL. And now you can use it without having to look around anymore :)
Using the code
In my working environment I don't have the right headers and libs to include in the project, so I used the functions inside the DLL using the LoadLibrary and GetProcAddress, like this:
typedef DWORD (_stdcall *TGetIfTable) (
MIB_IFTABLE *pIfTable, ULONG *pdwSize, BOOL bOrder );
...
TGetIfTable pGetIfTable;
...
pGetIfTable=(TGetIfTable)GetProcAddress(LoadLibrary("Iphlpapi.dll"),
"GetIfTable");
The key function of the DLL is GetIfTable. You have to call this function twice, first time to know how much memory space allocate, and then to fill the structure with the return values. In the OnInitDialog I get the right size of the adapters-table and I can fill the combo box with all the adapters descriptions
...
m_pTable=NULL;
m_dwAdapters=0;
ULONG uRetCode=pGetIfTable(m_pTable,&m_dwAdapters,TRUE);
if (uRetCode == 122 )
{
m_pTable=new MIB_IFTABLE[m_dwAdapters];
pGetIfTable(m_pTable,&m_dwAdapters,TRUE);
for (UINT i=0;i<m_pTable->dwNumEntries;i++)
{
MIB_IFROW Row=m_pTable->table[i];
char szDescr[MAXLEN_IFDESCR];
memcpy(szDescr,Row.bDescr,Row.dwDescrLen);
szDescr[Row.dwDescrLen]=0;
m_ctlCBAdapters.AddString(szDescr);
}
}
...
if everything has gone right a timer starts, and the UpdateCounters get called every 100ms
void CP01Dlg::UpdateCounters()
{
int nIndex=m_ctlCBAdapters.GetCurSel();
if (nIndex!=CB_ERR)
{
pGetIfTable(m_pTable,&m_dwAdapters,TRUE);
MIB_IFROW Row=m_pTable->table[nIndex];
m_strInfo.Format("Received %d, Sent %d",Row.dwInOctets,
Row.dwOutOctets);
UpdateData(FALSE);
}
}
That's all
I hope this snippet can save you some time. See you in my next article.