《UNIX 网络编程》 第三章课后习题第三题

xiaoxiao2021-02-28  192

试写一个名为inet_pton_loose的函数,它能处理如下情形:如果地址族为AF_INET且inet_pton返回0,那就调用inet_aton看是否成功;类似地,如果地址族为AF_INET6且inet_pton返回0,那么就调用inet_aton看是否成功,若成功返回其IPv4映射的IPv6地址。

#include <stdio.h> #include <stdlib.h> #include <arpa/inet.h> #include <sys/socket.h> #include <netinet/in.h> #include <string.h> /** 具体的转换过程,不做详细注释,有更好的实现方式 **/ int inet_pton_loose(int family,const char *strptr,void *addrptr) { int i = 0; if(inet_pton(family,strptr,addrptr) == 0){ struct in_addr v4addr; if(inet_aton(strptr,&v4addr) == 1){ if(family == AF_INET){ memcpy(addrptr,(void *)&v4addr,sizeof(struct in_addr)); return 1; } if(family == AF_INET6){ struct in6_addr v6addr; for(i=0;i<16;i++){ if(i<10) v6addr.s6_addr[i] = 0; if(i >= 10 && i < 12) v6addr.s6_addr[i] = 0xf; if(i >= 12 ) v6addr.s6_addr[i] = htonl(v4addr.s_addr)>>(16-i-1)*8; } memcpy(addrptr,(void *)&v6addr,sizeof(struct in6_addr)); return 1; } } return 0; } return 1; } /** 获取输入,辨别是IPv4 还是IPv6 并做相应的处,理完成后输出用户的输入。没有添加错误处理。 **/ int main(int argc,char **argv) { struct in_addr IPv4addr; struct in6_addr IPv6addr; const u_char *strptr; const char *AddrFlag4 = "AF_INET"; const char *AddrFlag6 = "AF_INET6"; if(strcmp(AddrFlag4,argv[1]) == 0){ if(inet_pton_loose(AF_INET,argv[2],(void *)&IPv4addr) == 1){ strptr = (u_char *)&IPv4addr; printf("%s---%d.%d.%d.%d\n",argv[1],strptr[0],strptr[1],strptr[2],strptr[3]); return 1; } } if(strcmp(AddrFlag6,argv[1]) == 0){ if(inet_pton_loose(AF_INET6,argv[2],(void *)&IPv6addr) == 1){ strptr = (u_char *)&IPv6addr; printf("%s---%d%d:%d%d:%d%d:%d%d:%d%d:%x%x:%d.%d.%d.%d\n",argv[1],strptr[0],strptr[1], strptr[2],strptr[3],strptr[4],strptr[5],strptr[6],strptr[7],strptr[8],strptr[9] ,strptr[10],strptr[11],strptr[12],strptr[13],strptr[14],strptr[15]); return 1; } } return 1; } #include "unp.h" in_addr_t inet_pton_loose(int family, const char *strptr,void *addrptr) { struct in_addr *ap = (struct in_addr *)addrptr; int result = 0; if((family == AF_INET) && (inet_pton(family,strptr,addrptr) == 0)) { printf("the net protocol is IPv4 str is %s\n",strptr); result = inet_aton(strptr,ap); printf("result is %d\n",result); if(result) return ap->s_addr; else return 0; } else if ((family == AF_INET6) && (inet_pton(family,strptr,addrptr) == 0)) { printf("the net protocol is IPv6\n"); result = inet_aton(strptr,ap); printf("result is %d\n",result); if(result) { return ap->s_addr; } else return 0; } return 0; } int main (int argc, char **argv) { //if argv[1] is zero, means AF_INET type, 1 for AF_INET6 type char s[20]; struct in_addr addr; in_addr_t addr_result = 0; if(argc < 2) { printf("usage: ./mytest <fa> <addr>\n"); return 1; } bzero(&addr,sizeof(struct in_addr)); memset(s,0,sizeof(s)); strcpy(s,argv[2]); if(atoi(argv[1]) == 0) { printf("the net protocol is IPv4\n"); addr_result = inet_pton_loose(AF_INET,s,(void *)&addr); printf("addr_result is %x\n",addr_result); } else if(atoi(argv[1]) == 1) { printf("the net protocol is IPv6\n"); addr_result = inet_pton_loose(AF_INET6,s,(void *)&addr); printf("addr_result is %x\n",addr_result); } return 0; }
转载请注明原文地址: https://www.6miu.com/read-18858.html

最新回复(0)