由“获取mac”到"SDK"

作者在 2008-06-10 17:03:02 发布以下内容
 
 
☆ 如何获取网卡的MAC地址?
进行网络底层编程时,这是一个大家都无法回避的问题,也是一个比较棘手的问题。就我所知道的方法有如下几种:
1 使用NetBois命令。
  在网上搜索,可以发现这是最常见的方法。不过有点复杂,使用起来也有限制,如果机器禁用了NetBois,那么这种方法就行不通了。
 
2 使用Winpcap Packet.dll中的PacketGetNetType函数。
  熟悉Winpcap的人都知道,Winpcap常规及推荐使用的是wpcap.dll,winpcap并没有提供对Packet.dll的API支持,在开发文档中没有关于Packet.dll的文档。因此使用这种方法不规范也比较麻烦(需要安装winpcap驱动)。
 
3 使用ipconfig /all命令获取,并写入管道,我们的程序再从管道种读取 "Physical Address. . . . . . . . . :"
  这是我在CSDN上看到的一种方法。很巧妙,不过也比较麻烦,特别是有多个网卡时就更不实用了。
 
4 使用GetAdaptersAddresses/GetAdaptersInfo函数。
  最简单的方法。但是在MSDN6.0中查询不到该函数。该函数是在Windows 2000以上的系统中才有的函数,VC++6.0默认所带的SDK是win98的,所以要使用这个函数,就需要安装相应的SDK,我的系统是"XP",因此就要安装“XPSP2 PSDK”。系统相关的SDK可以到微软官方下载。下面是XPSP2 PSDK的下载地址。
http://www.microsoft.com:80/msdownload/platformsdk/sdkupdate/XPSP2FULLInstall.htm
 
 
☆ 什么是SDK?
  
   微软每推出一个重要的windows版本,一般都会同时推出一个SDK(Software Development Kit)。SDK包含了开发该windows版本所需的windows函数和常数定义、API函数说明文档、相关工具和示例。SDK一般使用C语言,但不包括编译器。高版本VC++包括了SDK所有的头文件、帮助、示例和工具,不需要再安装SDK,低版本如VC++5.0则需要安装SDK。从windows 98开始,windows SDK叫Platform SDK(http://www.microsoft.com/downloads/details.aspx?FamilyId=A55B6B43-E24F-4EA3-A93E-40C0EC4F68E5&displaylang=en),包含最新的windows API函数的有关声明、例子。
 
 
☆如何安装实用新版的SDK?

  我安装的是“XPSP2 PSDK”。先到微软官方下载相关的安装文件。下载完毕你会发现并没有setup.exe或者install.exe之类
的安装主程序文件。查看下载页上的安装说明,原来需要先用PSDK-FULL.bat(下载页面上有该文件)对.cab文件进行解压缩。
命令格式是:“psdk-full 解压缩后的路径”,需要至少 1.4 GB 的空闲硬盘空间。解压缩可能需要好几分钟(我大概用了1分
钟吧)。
  解压缩完后,在解压出来的文件中就能找到“Setup.Exe”文件了。和安装普通程序一样安装就ok了。
   SDK安装完成后,还需要在VC++6.0中做相应的设置,然它能引用到SDK中的文件。
  (1)安装完毕后,打开VC++ 6.0,点Tools->Options->Directories选项卡,在Executable Files下,添加BIN文件
  
  (2)在Include Files添加Include文件:
  
  (3)在Library Files添加Lib文件:
  
   注意:添加成功以后,一定要用那个向上的箭头 把我们新添加的路径放在最上面,因为程序在编译过程中搜索路径的时候有优先搜索的功能。
 
☆使用GetAdaptersAddresses获取MAC地址(不能获取IP,NetMask,NetGate等信息)
 
#include<winsock2.h>
#include<Iphlpapi.h>
#include<stdio.h>
#pragma comment(lib,"Iphlpapi.lib")
int main()
{
 PIP_ADAPTER_ADDRESSES pAddresses;
 ULONG outBufLen = 0;
 DWORD dwRetVal = 0;
 
 pAddresses = (IP_ADAPTER_ADDRESSES*) malloc(sizeof(IP_ADAPTER_ADDRESSES));
 // 第一次使用 GetAdaptersAddresses 从 outBufLen 中获取需要的缓冲区大小
 if (GetAdaptersAddresses(AF_INET,
  0,
  NULL,
  pAddresses,
  &outBufLen) == ERROR_BUFFER_OVERFLOW)
 {
  GlobalFree(pAddresses);
  pAddresses = (IP_ADAPTER_ADDRESSES*) malloc(outBufLen);
 }
 
 // 第二次调用GetAdaptersAddresses 获取实际想获取的信息.
 if ((dwRetVal = GetAdaptersAddresses(AF_INET,
  0,
  NULL,
  pAddresses,
  &outBufLen)) == NO_ERROR)
 {
  while (pAddresses)
  {
   printf("AdapterName: %S\n",pAddresses->AdapterName);
   printf("Description: %S\n", pAddresses->Description);
   printf("PhysicalAddress: %02x-%02x-%02x-%02x-%02x-%02x\n\n",
                        pAddresses->PhysicalAddress[0],
         pAddresses->PhysicalAddress[1],
         pAddresses->PhysicalAddress[2],
         pAddresses->PhysicalAddress[3],
         pAddresses->PhysicalAddress[4],
         pAddresses->PhysicalAddress[5]);
   pAddresses = pAddresses->Next;
  }
 }
 else
  printf("Get Adapter Information failed!\n");
 return 0;
}
 
 
推荐!
☆使用GetAdaptersInfo获取网卡详细信息(包括:Adapter Name,Mac,Ip,NetMask,NetGate)
 
#include<winsock2.h>
#include<Iphlpapi.h>
#include<stdio.h>
#pragma comment(lib,"Iphlpapi.lib")
int main()
{
 PIP_ADAPTER_INFO pAdapterInfo;
 PIP_ADAPTER_INFO pAdapter = NULL;
 DWORD dwRetVal = 0;
 ULONG ulOutBufLen;
 pAdapterInfo=(PIP_ADAPTER_INFO)malloc(sizeof(IP_ADAPTER_INFO));
 ulOutBufLen = sizeof(IP_ADAPTER_INFO);
 
 // 第一次调用GetAdapterInfo获取ulOutBufLen大小
 if (GetAdaptersInfo( pAdapterInfo, &ulOutBufLen) == ERROR_BUFFER_OVERFLOW)
 {
  free(pAdapterInfo);
  pAdapterInfo = (IP_ADAPTER_INFO *) malloc (ulOutBufLen);
 }
 
 if ((dwRetVal = GetAdaptersInfo( pAdapterInfo, &ulOutBufLen)) == NO_ERROR) {
  pAdapter = pAdapterInfo;
  while (pAdapter)
  {
   printf("Adapter Name: \t%s\n", pAdapter->AdapterName);
   printf("Adapter Desc: \t%s\n", pAdapter->Description);
   printf("MAC Addr: \t%02x-%02x-%02x-%02x-%02x-%02x\n",
     pAdapter->Address[0],
     pAdapter->Address[1],
     pAdapter->Address[2],
     pAdapter->Address[3],
     pAdapter->Address[4],
     pAdapter->Address[5]);
   printf("IP Address: \t%s\n", pAdapter->IpAddressList.IpAddress.String);
   printf("IP Mask: \t%s\n", pAdapter->IpAddressList.IpMask.String);    
   printf("Gateway: \t%s\n", pAdapter->GatewayList.IpAddress.String);
   pAdapter = pAdapter->Next;
  }
 }
 else
 {
  printf("Call to GetAdaptersInfo failed.\n");
 }
}

本博客于即日起(2009.2.26)停止更新,

新博客地址:http://www.redicecn.cn ,

本博客的大部分文章已经转移到新博客中...


编程经验 | 阅读 11939 次
文章评论,共1条
redice(作者)
2008-06-18 15:33
1
注意“-&amp;gt;”对应的是“-&gt;”,这是被博客后台经过html代码过滤后的结果...
游客请输入验证码
浏览585032次