C语言网络编程(3)— 通过DNS连接到百度
一、gethostbyname()函数
我们现在认知一台计算机主机通常采用直观可读的名字。例如百度我们会记住 www.baidu.com 而不是他的IP地址。对于大多数的应用程序来说应该是处理名字而不是处理地址。如果说对于一个点分十进制来说还好记住,那么当使用IPv6时,IP地址就不是那么好记了。
而Linux下的函数 gethostbyname是查找主机名最基本的函数。如果调用成功,它就返回一个指向hostent结构的指针,该结构中含有所查找主机的所有IPv4地址。
函数原型如下:
struct hostent *gethostbyname(const char *name);
调用成功返回hostent结构体的指针,hostent结构体如下
struct hostent {
char *h_name;
char **h_aliases;
int h_addrtype;
int h_length;
char **h_addr_list;
}
注:一个地址有多个IP对应,比如一个大型网站可能南方,北方,国外等不同的地方都有主机,总之是很多情况,需要多个IP。
二、编程获取百度的IP地址
要使用gethostbyname()函数则需要导入头文件:
#include <netdb.h>
我们直接使用gethostbyname()获取百度域名的信息
struct hostent *host_ptr = gethostbyname("www.baidu.com");
然后将消息打印出来
printf("official name:%s \n",host_ptr->h_name);
for(i=0; host_ptr->h_aliases[i] != NULL; i++)
printf("alias name :%s \n",host_ptr->h_aliases[i]);
printf("address type :%s \n",host_ptr->h_addrtype == AF_INET ?"IPv4":"IPv6");
for(i=0; host_ptr->h_addr_list[i] != NULL; i++)
printf("addr %d :%s \n",i, inet_ntoa( *(struct in_addr*)host_ptr->h_addr_list[i]));
编译,运行结果如下:
然后我们在终端使用ping
命令,可以看到,我们同样得到了两个IP地址
三、连接百度服务器
尝试连接到百度服务器
int tcp_client = socket(AF_INET, SOCK_STREAM, 0);
if (-1 == tcp_client)
{
perror("socket");
return -1;
}
struct sockaddr_in server_addr = {0};
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(80);
server_addr.sin_addr.s_addr = *(in_addr_t*)host_ptr->h_addr_list[0];
ret = connect(tcp_client, (const struct sockaddr *)&server_addr, sizeof(server_addr));
if (ret < 0)
perror("connect");
else
printf("connect result, ret = %d.\n", ret);
连接成功:
然后发送一个GET请求,
char sendbuf[]={"GET / HTTP/1.1\n\n"};
ret = send(tcp_client, sendbuf, strlen(sendbuf),0);
char recvbuf[1024] = {0};
ret = recv(tcp_client, recvbuf, sizeof(recvbuf), 0);
printf("Recvdate: \n%s \n",recvbuf);
编译,运行,访问成功
四、代码
#include <stdio.h>
#include <string.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <netdb.h>
int main(void)
{
int ret,i=0;
struct hostent *host_ptr = gethostbyname("www.baidu.com");
printf("official name:%s \n",host_ptr->h_name);
for(i=0; host_ptr->h_aliases[i] != NULL; i++)
printf("alias name :%s \n",host_ptr->h_aliases[i]);
printf("address type :%s \n",host_ptr->h_addrtype == AF_INET ?"IPv4":"IPv6");
for(i=0; host_ptr->h_addr_list[i] != NULL; i++)
printf("addr %d :%s \n",i, inet_ntoa( *(struct in_addr*)host_ptr->h_addr_list[i]));
int tcp_client = socket(AF_INET, SOCK_STREAM, 0);
if (-1 == tcp_client)
{
perror("socket");
return -1;
}
struct sockaddr_in server_addr = {0};
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(80);
server_addr.sin_addr.s_addr = *(in_addr_t*)host_ptr->h_addr_list[0];
ret = connect(tcp_client, (const struct sockaddr *)&server_addr, sizeof(server_addr));
if (ret < 0)
perror("connect");
else
printf("connect success.\n");
char sendbuf[]={"GET / HTTP/1.1\n\n"};
ret = send(tcp_client, sendbuf, strlen(sendbuf),0);
char recvbuf[1024] = {0};
ret = recv(tcp_client, recvbuf, sizeof(recvbuf), 0);
printf("Recvdate: \n%s \n",recvbuf);
close(tcp_client);
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)