曲径通幽论坛

 找回密码
 立即注册
搜索
查看: 6888|回复: 0
打印 上一主题 下一主题

inet 系列函数

[复制链接]

4918

主题

5880

帖子

3万

积分

GROAD

曲径通幽,安觅芳踪。

Rank: 6Rank: 6

积分
34387
跳转到指定楼层
楼主
发表于 2009-7-16 16:30:21 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
通常习惯字符串形式的网络地址如 192.168.2.100,但在网络上进行数据通信时,需要使用的是二进制形式且为网络字节顺序的 IP 地址,如 "192.168.2.100" 对应的二进制形式为:0x6402a8c0

Linux 系统为网络地址的格式转换提供了一系列函数,man inet 获得原型如下:
 
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
int inet_aton(const char *cp, struct in_addr *inp);
in_addr_t inet_addr(const char *cp);
in_addr_t inet_network(const char *cp);
char *inet_ntoa(struct in_addr in);
struct in_addr inet_makeaddr(int net, int host);
in_addr_t inet_lnaof(struct in_addr in);
in_addr_t inet_netof(struct in_addr in);
int inet_pton(int af, const char *src, void *dst);

const char *inet_ntop(int af, const void *src, char *dst, socklen_t size);
1、inet_aton()
inet_aton() 将参数 cp 指向的字符串形式的 IP 地址转换为二进制的网络字节顺序的 IP 地址,转换后的结果存于参数 inp 所指向的空间中。执行成功返回非 0 值,参数无效返回 0.
2、inet_addr()
与 inet_aton() 类似,执行成功时将转换后的结果返回,参数无效返回 INADDR_NONE (该值一般为 -1)。
注意,此函数已经过时,推荐使用 inet_aton()。因为对于有效地址 "255.255.255.255" 它也返回 -1 (因为 -1 的补码形式为 0xFFFFFFFF ),使得用户可能将 255.255.255.255 也当成是无效的非法地址,而使用 inet_aton() 则不存在这个问题。
      
3、inet_network()
inet_network() 将参数 cp 所指向的字符串形式的网络地址转换为主机字节顺序形式的二进制 IP 地址,执行成功后返回转换后的结果,参数无效返回  -1 。

4、inet_ntoa()
该函数将值为 in 的网络字节顺序形式的二进制 IP 地址转换成以 "." 分隔的字符串形式,执行成功返回结果字符串的指针,参数无效返回 NULL 。

5、inet_makeaddr()
该函数将网络号为参数 net ,主机号为参数 host 的两个地址组合成一个网络地址,如 net 取 0xc0a802 (192.168.2.0 ,C 类网络,主机字节顺序形式),host 取 0x64 ( 主机号 0.0.0.100 ,主机字节顺序形式 ),则组合后的网络地址为:192.168.2.100,并表示为网络字节顺序形式 0x6402a8c0 。

6、inet_lnaof()
该函数从参数 in 中提取出主机地址,执行成功后返回主机字节顺序形式的主机地址。如 192.168.2.100 属于 C 类地址,则主机号为低 8 位,主机地址为 0.0.0.100 ,按主机字节顺序输出则为 0x64。

7、inet_netof()
该函数从参数 in 中提取出网络地址,执行成功返回主机字节顺序形式的网络地址。如 192.168.2.100,属于 C 类地址,则高 24 位表示网络号,网络地址为 192.168.2.0 ,按主机字节顺序输出则为 0xc0a802.

8. inet_pton()
该函数将存储再起始位置为 cp,地址协议类型为 AF 的点分十进制地址转换到 buf 中,af 的类型如果是 IPV4,则 buf 类型应该为 struct in_addr;如果 af 的类型是 IPV6,buf 类型应该为 struct in6_addr 。

9. inet_ntop()
该函数将以网络字节顺序方式存储再起始位置为 src,地址协议类型为 AF 的 32 位 IP 信息转换为点分十进制方式,并存储在长度为 len 大小的 buf 中,af 的类型如果是 IPV4,则 buf 类型应该为 struct in_addr;如果 af 的类型是 IPV6,buf 类型应该为 struct in6_addr 。


测试代码
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>

int main()
{
    char        buffer[32];
    int        ret = 0;
    int         host = 0;
    int         network = 0;
    unsigned int     address = 0;
    struct in_addr in;
   
    in.s_addr = 0;
    /*输入一个以 "." 分隔的字符串形式的IP地址*/
    printf("please input your ip address:");
        fgets(buffer, 31, stdin);
    buffer[31] = '\0';
   
    /*测试使用 inet_aton() 函数*/
    if ((ret = inet_aton(buffer, &in)) == 0) {
        printf("inet_aton: \tinvailid address\n");
    } else {
        printf("inet_aton: \t0x%x\n", in.s_addr);
    }

    /*测试使用 inet_addr() 函数*/
    if ((address = inet_addr(buffer)) == INADDR_NONE) {
        printf("inet_addr: \tinvalid address \n");
    } else {   
       printf("inet_addr:\t0x%lx\n", address);
    }

    /*测试使用 inet_netwrok()函数*/
    if ((address = inet_network(buffer)) == -1) {
        printf("inet_network: \tinvalid address\n");
    } else {
       printf("inet_network:\t0x%lx\n", address);
    }

    /*测试使用 inet_ntoa() 函数*/
    if (inet_ntoa(in) == NULL) {
        printf("inet_ntoa: \tinvalid address\n");
    } else {
       printf("inet_ntoa: \t%s\n", inet_ntoa(in));
    }

    /*测试使用 inet_lnaof() 与 inet_netof() 函数*/
    host = inet_lnaof(in);
    network = inet_netof(in);
    printf("inet_lnaof:\t0x%x\n", host);
    printf("inet_netof:\t0x%x\n", network);

    in = inet_makeaddr(network, host);
    printf("inet_makeaddr:0x%x\n", in.s_addr);

    return 0;
}

运行及输出
beyes@linux-beyes:~/C/network> ./test_address.exe
please input your ip address:192.168.2.100
inet_aton:     0x6402a8c0
inet_addr:    0x6402a8c0
inet_network:    0xc0a80264
inet_ntoa:     192.168.2.100
inet_lnaof:    0x64
inet_netof:    0xc0a802
inet_makeaddr:0x6402a8c0

inet_pton() 和 inet_ntop() 用法
#include <arpa/inet.h>
#include <netinet/in.h>
#include <stdio.h>
#include <string.h>
#include <sys/socket.h>

int main (int argc, char **argv)
{
    struct in_addr net_addr, ret;
    char buf[128];

    inet_pton (AF_INET, "192.168.2.102", &ret);
    printf ("%x\n", ret.s_addr);

    inet_ntop (AF_INET, &ret, buf, 128);
    printf ("buf=%s\n", buf);

    return (0);
}
运行与输出
./inet_pton
6602a8c0
buf=192.168.2.102
说明
第 1 行就是 192.168.2.102 转化为网络字节顺序的十六进制无符号整型数;第 2 行是把网络字节顺序转化为点分十进制的字符串。

struct in_addr 结构体的定义在 /usr/include/netinet/in.h 里:
/* Internet address.  */
typedef uint32_t in_addr_t;
struct in_addr
  {
    in_addr_t s_addr;
  };
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|曲径通幽 ( 琼ICP备11001422号-1|公安备案:46900502000207 )

GMT+8, 2024-5-20 19:54 , Processed in 0.066683 second(s), 22 queries .

Powered by Discuz! X3.2

© 2001-2013 Comsenz Inc.

快速回复 返回顶部 返回列表