windows 平台c++代码获取物理地址

头文件IPApi.h

#pragma once

// Returns number of NICs
// 'address' contains the physical address of index='idx'
int get_physical_address(char * address, int idx);

// Returns number of NICs
// 'address' contains the physical address of index=0
int get_first_physical_address(char * address);

bool is_physical_address(const char * address);

源文件IPApi.cpp

#include "IPApi.h"
#include <winsock2.h>
#include <iphlpapi.h>
#include <stdio.h>
#include <stdlib.h>

#pragma comment(lib, "IPHLPAPI.lib")

#define WORKING_BUFFER_SIZE 15000

#define MALLOC(x) HeapAlloc(GetProcessHeap(), 0, (x))
#define FREE(x) HeapFree(GetProcessHeap(), 0, (x))

static void phy_adapter_address2str(PIP_ADAPTER_ADDRESSES paddress, char * saddress) {
    int j = 0;
    for (int i = 0; i < (int)paddress->PhysicalAddressLength; i++) {
        j += sprintf(saddress + j, "%.2X", (int)paddress->PhysicalAddress[i]);
    }
}

static ULONG get_adapters_Addresses(PIP_ADAPTER_ADDRESSES * pAddresses) {
    DWORD dwRetVal = 0;
    ULONG Iterations = 0;
    const ULONG MAX_TRIES = 3;
    do {
        ULONG outBufLen = WORKING_BUFFER_SIZE;
        *pAddresses = (IP_ADAPTER_ADDRESSES *)MALLOC(outBufLen);
        if (*pAddresses == NULL) {
            printf("Memory allocation failed for IP_ADAPTER_ADDRESSES struct\n");
            exit(1);
        }
        dwRetVal = GetAdaptersAddresses(AF_UNSPEC, GAA_FLAG_INCLUDE_PREFIX, NULL, *pAddresses, &outBufLen);
        if (dwRetVal == ERROR_BUFFER_OVERFLOW) {
            FREE(*pAddresses);
            *pAddresses = NULL;
        }
        else {
            break;
        }
        Iterations++;
    } while ((dwRetVal == ERROR_BUFFER_OVERFLOW) && (Iterations < MAX_TRIES));

    return dwRetVal;
}

int get_first_physical_address(char * address) {
    return get_physical_address(address, 0);
}

int get_physical_address(char * address, int idx) {
    PIP_ADAPTER_ADDRESSES pAddresses = NULL;
    DWORD dwRetVal = get_adapters_Addresses(&pAddresses);

    int countOfAddress(0);
    if (dwRetVal == NO_ERROR) {
        PIP_ADAPTER_ADDRESSES pCurrAddresses = pAddresses;
        while (pCurrAddresses) {
            if (pCurrAddresses->PhysicalAddressLength != 0) {
                if (idx == countOfAddress) {
                    phy_adapter_address2str(pCurrAddresses, address);
                }
                countOfAddress++;
            }
            pCurrAddresses = pCurrAddresses->Next;
        }
    } else {}

    if (pAddresses) {
        FREE(pAddresses);
    }
    return countOfAddress;
}

bool is_physical_address(const char * address) {
    PIP_ADAPTER_ADDRESSES pAddresses = NULL;
    DWORD dwRetVal = get_adapters_Addresses(&pAddresses);

    int cmp_out(1); // default not address
    if (dwRetVal == NO_ERROR) {
        PIP_ADAPTER_ADDRESSES pCurrAddresses = pAddresses;
        while (pCurrAddresses) {
            if (pCurrAddresses->PhysicalAddressLength != 0) {
                char s[25] = { 0 };
                phy_adapter_address2str(pCurrAddresses, s);
                cmp_out = strcmp(address, s);
                if (cmp_out == 0) {
                    break;
                }
            }
            pCurrAddresses = pCurrAddresses->Next;
        }
    }
    else {}

    if (pAddresses) {
        FREE(pAddresses);
    }
    return (cmp_out == 0 ? true : false);
}

猜你喜欢

转载自blog.csdn.net/iceboy314159/article/details/93663666