上一篇说的是为NDK设置静态IP,但是有时会有IP冲突,那还要更改程序进行IP的更改就会太麻烦了,自然就会有了动态IP。
动态IP其实就是启动DHCP服务。
而什么是DHCP呢?
DHCP(Dynamic Host Configuration Protocol,动态主机配置协议)通常被应用在大型的局域网络环境中,主要作用是集中的管理、分配IP地址,使网络环境中的主机动态的获得IP地址、 Gateway地址、DNS服务器地址等信息,并能够提升地址的使用率。
DHCP有三种机制分配IP地址:
1) 自动分配方式(Automatic Allocation),DHCP服务器为主机指定一个永久性的IP地址,一旦DHCP客户端第一次成功从DHCP服务器端租用到IP地址后,就可以永久性的使用该地址。
2) 动态分配方式(Dynamic Allocation),DHCP服务器给主机指定一个具有时间限制的IP地址,时间到期或主机明确表示放弃该地址时,该地址可以被其他主机使用。
3) 手工分配方式(Manual Allocation),客户端的IP地址是由网络管理员指定的,DHCP服务器只是将指定的IP地址告诉客户端主机。
三种地址分配方式中,只有动态分配可以重复使用客户端不再需要的地址。
回到正题,NDK中DHCP的配置主要是使用CI_SERVICE_DHCPC结构体。
CI_SERVICE_DHCPC结构体主要有两个成员,如下图:
其中又包含了CISARGS结构体与NTPARAM_DHCP结构体。
CISARGS结构体:
![](https://i-blog.csdnimg.cn/blog_migrate/810e261efe7bc4952c51a206cc53cc74.png)
Item这是添加到配置时使用的项目值的副本。
hService服务请求的句柄。
Mode模式参数是表示服务所需执行行为的标志集合,它的值有以下几个:
![](https://i-blog.csdnimg.cn/blog_migrate/08656df021e0742a6f30a5dc78a03b42.png)
Status
网络控制服务回调检测的服务状态。
![](https://i-blog.csdnimg.cn/blog_migrate/459ac37b7029db0a69bbe9a7d4a9de5a.png)
IFIdx
是物理设备的编号。
IPAddr
是服务初始化时的
IP
地址。
最后一个函数指针是回调函数。
这个函数在程序中的实现为:
- void ServiceReport(unsigned int Item, unsigned int Status, unsigned int Report, HANDLE h)
- {
- platform_write("Service Status: %9s: %9s: %9s: %03d\n",
- TaskName[Item - 1], StatusStr[Status], ReportStr[Report / 256], Report & 0xFF);
- // 配置 DHCP
- if(Item == CFGITEM_SERVICE_DHCPCLIENT &&
- Status == CIS_SRV_STATUS_ENABLED &&
- (Report == (NETTOOLS_STAT_RUNNING|DHCPCODE_IPADD) ||
- Report == (NETTOOLS_STAT_RUNNING|DHCPCODE_IPRENEW)))
- {
- IPN IPTmp;
- // 配置 DNS
- IPTmp = inet_addr(DNSServer);
- if(IPTmp)
- {
- CfgAddEntry(0, CFGTAG_SYSINFO, CFGITEM_DHCP_DOMAINNAMESERVER, 0, sizeof(IPTmp), (UINT8 *)&IPTmp, 0);
- }
- // DHCP 状态
- DHCPStatus();
- }
- // 重置 DHCP 客户端服务
- if(Item == CFGITEM_SERVICE_DHCPCLIENT && (Report & ~0xFF) == NETTOOLS_STAT_FAULT)
- {
- CI_SERVICE_DHCPC dhcpc;
- int tmp;
- // 取得 DHCP 入口数据(传递到 DHCP_reset 索引)
- tmp = sizeof(dhcpc);
- CfgEntryGetData(h, &tmp, (UINT8 *)&dhcpc);
- // 创建 DHCP 复位任务(当前函数是在回调函数中执行所以不能直接调用该函数)
- TaskCreate(DHCPReset, "DHCPreset", OS_TASKPRINORM, 0x1000, dhcpc.cisargs.IfIdx, 1, 0);
- }
- }
NTPARAM_DHCP结构体:
![](https://i-blog.csdnimg.cn/blog_migrate/ee9aa4181a69c618862094ddabde714c.png)
pOptions
是一个指向
DHCP
配置的指针。
而
len
是指
pOptions
的长度。
最后DHCP的配置如下:
- bzero(&dhcpc, sizeof(dhcpc));
- dhcpc.cisargs.Mode = CIS_FLG_IFIDXVALID;
- dhcpc.cisargs.IfIdx = 1;
- dhcpc.cisargs.PCBSrv = &ServiceReport;
- dhcpc.param.pOptions = DHCP_OPTIONS;
- dhcpc.param.len = 2;
- CfgAddEntry(hCfg, CFGTAG_SERVICE, CFGITEM_SERVICE_DHCPCLIENT, 0, sizeof(dhcpc), (UINT8 *)&dhcpc, 0);
仍然是用
CfgAddEntry()
函数将
DHCP
的配置添加到
hCfg
句柄中。
由于接下来的几篇都是NDK的讲解与使用方法的说明,在NDK的最后一篇将把所有的源码与二进制文件上传。