#include <sys/socket.h>
#include <netdb.h> int getaddrinfo(const char *restrict nodename, /* host 或者IP地址 */
const char *restrict servname, /* 十进制端口号 或者常用服务名称如"ftp"、"http"等 */
const struct addrinfo *restrict hints, /* 获取信息要求设置 */
struct addrinfo **restrict res); /* 获取信息结果 */ void freeaddrinfo(struct addrinfo *ai); 

Data Structure

http://www.cnblogs.com/LubinLew/p/POSIX-DataStructure.html#struct_addrinfo

Description

IPv4中使用gethostbyname()函数完成主机名到地址解析,这个函数仅仅支持IPv4,

且不允许调用者指定所需地址类型的任何信息,返回的结构只包含了用于存储IPv4地址的空间。

IPv6中引入了新的API getaddrinfo(),它是协议无关的,既可用于IPv4也可用于IPv6。

getaddrinfo() 函数能够处理名字到地址以及服务到端口这两种转换,返回的是一个 struct addrinfo 的结构体(列表)指针而不是一个地址清单。

这些 struct addrinfo 结构体随后可由套接口函数直接使用。如此以来,getaddrinfo()函数把协议相关性安全隐藏在这个库函数内部。

应用程序只要处理由getaddrinfo()函数填写的套接口地址结构。

Parameter

1) nodename

主机名("www.baidu.com")或者是数字化的地址字符串(IPv4的点分十进制串("192.168.1.100")或者IPv6的16进制串("2000::1:2345:6789:abcd")),

如果 ai_flags 中设置了AI_NUMERICHOST 标志,那么该参数只能是数字化的地址字符串,不能是域名,

该标志的作用就是阻止进行域名解析。

nodename 和 servname 可以设置为NULL,但是同时只能有一个为NUL。

2) servname

服务名可以是十进制的端口号("8080")字符串,也可以是已定义的服务名称,如"ftp"、"http"等,详细请查看/etc/services 文件,

最后翻译成对应服务的端口号。如果此参数设置为NULL,那么返回的socket地址中的端口号不会被设置。

如果 ai_flags 设置了AI_NUMERICSERV 标志并且该参数未设置为NULL,那么该参数必须是一个指向10进制的端口号字符串,

不能设定成服务名,该标志就是用来阻止服务名解析。

3) hints

该参数指向用户设定的 struct addrinfo 结构体,只能设定该结构体中 ai_family、ai_socktype、ai_protocol 和 ai_flags 四个域,

其他域必须设置为0 或者 NULL, 通常是申请 结构体变量后使用memset()初始化再设定指定的四个域。

该参数可以设置为NULL,等价于 ai_socktype = 0, ai_protocol = 0,ai_family = AF_UNSPEC,

ai_flags = 0 (在GNU Linux中ai_flag = AI_V4MAPPED | AI_ADDRCONFIG,可以看作是GNU的改进)。

 ① ai_family

  指定返回地址的协议簇,取值范围:AF_INET(IPv4)、AF_INET6(IPv6)、AF_UNSPEC(IPv4 and IPv6)

② ai_socktype

  具体类型请查看struct addrinfo 中的 enum __socket_type 类型,用于设定返回地址的socket类型,

  常用的有SOCK_STREAM、SOCK_DGRAM、SOCK_RAW, 设置为0表示所有类型都可以。

 ③ ai_protocol

  具体取值范围请查看 Ip Protocol ,常用的有 IPPROTO_TCP、IPPROTO_UDP 等,设置为0表示所有协议。

 ④ ai_flags

  附加选项,多个选项可以使用或操作进行结合,具体取值范围请查看struct addrinfo , 常用的标志如下:

  • AI_PASSIVE

    如果设置了 AI_PASSIVE 标志,并且 nodename 是 NULL, 那么返回的socket地址可以用于的bind()函数,

  返回的地址是通配符地址(wildcard address, IPv4时是INADDR_ANY,IPv6时是IN6ADDR_ANY_INIT),

  这样应用程序(典型是server)就可以使用这个通配符地址用来接收任何请求主机地址的连接,

  如果 nodename 不是NULL,那么 AI_PASSIVE 标志被忽略;

    如果未设置AI_PASSIVE标志,返回的socket地址可以用于connect(), sendto(), 或者 sendmsg()函数。

    如果 nodename 是NULL,那么网络地址会被设置为lookback接口地址(IPv4时是INADDR_LOOPBACK,IPv6时是IN6ADDR_LOOPBACK_INIT),

    这种情况下,应用是想与运行在同一个主机上另一个应用通信。

  • AI_CANONNAME

    请求canonical(主机的official name)名字。如果设置了该标志,那么 res 返回的第一个 struct addrinfo 中的 ai_canonname 域会存储official name的指针。

  • AI_NUMERICHOST

    阻止域名解析,具体见 nodename 中的说明。

  • AI_NUMERICSERV

    阻止服务名解析,具体见 servname中的说明。

  • AI_V4MAPPED

    当 ai_family 指定为AF_INT6(IPv6)时,如果没有找到IPv6地址,那么会返回IPv4-mapped IPv6 地址,

    也就是说如果没有找到AAAA record(用来将域名解析到IPv6地址的DNS记录),那么就查询A record(IPv4),

    将找到的IPv4地址映射到IPv6地址, IPv4-mapped IPv6 地址其实是IPv6内嵌IPv4的一种方式,

    地址的形式为"0::FFFF:a.b.c.d",例如"::ffff:192.168.89.9"(混合格式)这个地址仍然是一个IPv6地址,

只是"0000:0000:0000:0000:0000:ffff:c0a8:5909"(16机制格式)的另外一种写法罢了。

    当 ai_family 不是AF_INT6(IPv6)时,该标志被忽略。

  • AI_ALL

    查询IPv4和IPv6地址

  • AI_ADDRCONFIG

    只有当主机配置了IPv4地址才进行查询IPv4地址;只有当主机配置了IPv6地址才进行查询IPv6地址.

4) res

该参数获取一个指向存储结果的 struct addrinfo 结构体列表,使用完成后调用 freeaddrinfo() 释放存储结果空间。

Return Value

如果 getaddrinfo() 函数执行成功,返回值为 0 , 其他情况返回值表示错误种别。使用函数gai_strerror() 可以获取可读性的错误信息,用法用strerror()相同,

错误种别如下:

  • EAI_ADDRFAMILY

    指定的主机上没有请求的address family对应的网络地址.

  • EAI_AGAIN

    DNS(name server)返回临时性错误. 可以稍后重试.

  • EAI_BADFLAGS

    hints.ai_flags 包含了无效的标志; 或者 hints.ai_flags 包含了 AI_CANONNAME 标志但是 name 是 NULL.

  • EAI_FAIL

    DNS(name server)返回永久性错误

  • EAI_FAMILY

    不支持的 address family(hints.ai_family).

  • EAI_MEMORY

    内存耗尽.

  • EAI_NODATA

    指定的网络主机存在,但是其未定义任何网络地址.

  • EAI_NONAME

    nodename 或者 servname 未知;或者两者都设置为NULL;

    或者设置了 AI_NUMERICSERV 标志但是 servname 不是一个数字化的端口名字符串。

  • EAI_SERVICE

    请求的socket类型不支持请求的服务类型.例如服务类型是 "shell" (基于流的socket服务),

    但是 hints.ai_protocol 是  IPPROTO_UDP 或者hints.ai_socktype 是 SOCK_DGRAM;

    或者 servname 不是NULL 但是 hints.ai_socktype 是 SOCK_RAW (原始套接字不支持服务的概念).

  • EAI_SOCKTYPE

    不支持请求的socket类型. 例如, hints.ai_socktype 和 hints.ai_protocol 冲突 (例如分别是SOCK_DGRAM、IPPROTO_TCP).

  • EAI_SYSTEM

    系统调用错误,检查 errno.

Example

man getaddrinfo 最后有客户端和服务器端2个例子。

转自:http://www.cnblogs.com/LubinLew/p/POSIX-getaddrinfo.html

getaddrinfo详解的更多相关文章

  1. getaddrinfo()详解

    IPv4中使用gethostbyname()函数完成主机名到地址解析,但是该API不允许调用者指定所需地址类型的任何信息,返回的结构只包含 了用于存储IPv4地址的空间.为了解决该问题,IPv6中引入 ...

  2. Linq之旅:Linq入门详解(Linq to Objects)

    示例代码下载:Linq之旅:Linq入门详解(Linq to Objects) 本博文详细介绍 .NET 3.5 中引入的重要功能:Language Integrated Query(LINQ,语言集 ...

  3. 架构设计:远程调用服务架构设计及zookeeper技术详解(下篇)

    一.下篇开头的废话 终于开写下篇了,这也是我写远程调用框架的第三篇文章,前两篇都被博客园作为[编辑推荐]的文章,很兴奋哦,嘿嘿~~~~,本人是个很臭美的人,一定得要截图为证: 今天是2014年的第一天 ...

  4. EntityFramework Core 1.1 Add、Attach、Update、Remove方法如何高效使用详解

    前言 我比较喜欢安静,大概和我喜欢研究和琢磨技术原因相关吧,刚好到了元旦节,这几天可以好好学习下EF Core,同时在项目当中用到EF Core,借此机会给予比较深入的理解,这里我们只讲解和EF 6. ...

  5. Java 字符串格式化详解

    Java 字符串格式化详解 版权声明:本文为博主原创文章,未经博主允许不得转载. 微博:厉圣杰 文中如有纰漏,欢迎大家留言指出. 在 Java 的 String 类中,可以使用 format() 方法 ...

  6. Android Notification 详解(一)——基本操作

    Android Notification 详解(一)--基本操作 版权声明:本文为博主原创文章,未经博主允许不得转载. 微博:厉圣杰 源码:AndroidDemo/Notification 文中如有纰 ...

  7. Android Notification 详解——基本操作

    Android Notification 详解 版权声明:本文为博主原创文章,未经博主允许不得转载. 前几天项目中有用到 Android 通知相关的内容,索性把 Android Notificatio ...

  8. Git初探--笔记整理和Git命令详解

    几个重要的概念 首先先明确几个概念: WorkPlace : 工作区 Index: 暂存区 Repository: 本地仓库/版本库 Remote: 远程仓库 当在Remote(如Github)上面c ...

  9. Drawable实战解析:Android XML shape 标签使用详解(apk瘦身,减少内存好帮手)

    Android XML shape 标签使用详解   一个android开发者肯定懂得使用 xml 定义一个 Drawable,比如定义一个 rect 或者 circle 作为一个 View 的背景. ...

随机推荐

  1. int类中的方法

    我们知道在python中,一切对象都是类,对象的方法都封装在类中,现在来探讨一下int类中的方法: 我们可以通过help(int)和dir(int)来查看int类中都封装了那些方法:     1.bi ...

  2. chrome浏览器使用HTML5预览图片

    chrome浏览器对HTML5支持的较好,使用HTML5的File相关的api,可以实现前台页面在选定图片后,不上传即可预览.代码如下: 1.前台代码,使用<input type="f ...

  3. 搭建 GIT 服务器

    Git 是一款免费.开源的分布式版本控制系统,用于敏捷高效地处理任何或小或大的项目. 此实验以 CentOS 7.2 x64 的系统为环境,搭建 git 服务器. 安装依赖库和编译工具 为了后续安装能 ...

  4. JSP内置对象——request对象

    request对象request对象封装了由客户端生成的HTTP请求的所有细节,主要包括HTTP头信息.系统信息.请求方式和请求参数等. 通过request对象提供的各种方法可以处理客户端浏览器提交的 ...

  5. spring杂碎

    spring优点 方便解耦,简化开发 Spring就是一个大工厂,可以将所有对象创建和依赖关系维护,交给Spring管理 AOP编程的支持 Spring提供面向切面编程,可以方便的实现对程序进行权限拦 ...

  6. FastReport.Net使用:[17]线(Line)控件使用

    FastReport中,线(Line)控件怎么用?怎么画一条美观的线? 认识Line控件 1.线(Line)控件包含于形状(Shape)控件中,有5个可选项,一个标准线和四个对角线,其实都是同一种线, ...

  7. Hibernate 单项一对多的关联映射

    在上一篇中我们简单介绍了多对一的关联映射,本文介绍hibernate中一对多的关联映射. 1.设计表结构 虽然关联关系由多对一变为一对多,但是我们表结构不会发生改变,只是指向变了. 2.创建stude ...

  8. 【插头DP】BZOJ1187- [HNOI2007]神奇游乐园

    [题目大意] 在n*m的网格中选一条回路,使权值和最大. [思路] 和之前裸的插头DP差不多,只不过现在回路不需要经过所有的格子.所以有以下几个注意点(具体看注释): (1)left和up插头相等的时 ...

  9. setResult()的调用时机

    今天遇到这样一个问题,我在Activity-A中用startActivityForResult()方法启动了Activity-B,并且在B中通过setResult()方法给A返回值,由于某些原因不能在 ...

  10. C# -- 学习笔记之基础篇

    由于要做一个系统,需要用到搜索引擎开发的很多知识点.对于开发语言的选择,我一般不是擅长什么才选择什么的,而是通过对比之后,考虑开发时间和难易程度来选择.尽管现在的开发经验还不足,也只能凭借自己弱弱的判 ...