[10]Linux网络编程

[1]Socket简介:

Linux中的网络编程通过Socket(套接字)接口实现,Socket是一种文件描述符。
套接字socket有三种类型:

  • 流式套接字(SOCK_STREAM):流式的套接字使用TCP协议,可以提供可靠的、面向连接的通讯流。
  • 数据报套接字(SOCK_DGRAM):数据报套接字使用UDP协议定义了一种无连接的服务,数据通过相互独立的报文进行传输,是无序的,并且不保证可靠,无差错。
  • 原始套接字(SOCK_RAW):原始套接字允许对低层协议如IP或ICMP直接访问,主要用于新的网络协议的测试等。

[2]网络地址:

sockaddr:

Linux中的网络地址有sockaddr结构体指定:

#include <netinet/in.h>
struct sockaddr {
unsigned  short  sa_family;     /* address family, AF_xxx */
char  sa_data[14];              /* 14 bytes of protocol address */
};
//sa_family是地址家族,一般都是“AF_xxx”的形式,IPV4的值为AF_INET。
//sa_data是14字节协议地址。

sockaddr_in:

sockaddr结构体等价于sockaddr_in结构体:

#include <netinet/in.h>
struct sockaddr_in
{
short int sin_family; /* Internet地址族 */
unsigned short int sin_port; /* 端口号 */
struct in_addr sin_addr; /* IP地址 */
unsigned char sin_zero[8]; /* 填0 */
}
struct in_addr
{
unsigned long s_addr;
}
//s_addr: 32位的地址(IP)。

地址转换函数:

字符串IP地址转换为struct in_addr:

#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
int inet_aton(const char *string, struct in_addr *addr);
  • 输入参数string包含ASCII表示的IP地址。
  • 输出参数addr是将要用新的IP地址更新的结构。
  • 返回值:如果这个函数成功,函数的返回值非零。如果输入地址不正确则会返回零。

sruct in_addr转换为字符串IP地址:

#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
char *inet_ntoa(struct in_addr in);

主机名与IP地址:

#include <netdb.h>
#include <sys/socket.h>
struct hostent *gethostbyname(const char *name);
//name:域名或者主机名
//返回值:目标主机的信息(如果函数调用错误,返回值是NULL)
struct hostent {
     char *h_name;//主机的规范名
     char **h_aliases;//主机的别名
     int h_addrtype;//主机ip地址的类型,IPV4(AF_INET)
     int h_length;//IP地址的个数
     char **h_addr_list;//IP地址列表
};
#define h_addr h_addr_list[0] /* 主机的第一个IP地址*/

[3]字节序转换:

待续

[4]Socket常用函数:

socket

socket()系统调用创建一个套接字并返回一个描述符,该描述符可以用来访问该套接字。

#include <sys/types.h>
#include <sys/socket.h>
int socket(int domain, int type, int protocol);
  • domain协议族:常用的协议族有:AF_INET(IPV4)、AF_INET6(IPV6)、AF_LOCAL(或称AF_UNIX,Unix域socket)、AF_ROUTE等。
  • type套接字类型:常用的类型有:SOCK_STREAM、SOCK_DGRAM、SOCK_RAW、SOCK_PACKET、SOCK_SEQPACKET等。
  • protocol协议类型:常用的协议有IPPROTO_TCP、IPPTOTO_UDP等。
  • 返回值:socket套接字。

bind

bind()函数将socket与本机的特定地址相关联(绑定)。

#include <sys/types.h>
#include <sys/socket.h>
int bind(int sockfd, const struct sockaddr *addr, socklen_t addrlen);
  • sockfd:socket文件描述符。
  • addr:由IP地址和端口号组成的网络终结点地址。
  • addrlen:addr的长度。
  • 返回值:bind在调用成功时返回0,失败是返回-1。

listen

宣告该套接字可接受连接,并建立一个队列来保存未处理的请求。

#include <sys/socket.h>
int listen(int socket, int backlog);
  • backlog:设置队列中可以容纳的未处理连接的最大个数,backlog常用值为5。
  • 返回值:成功时返回0,失败时返回-1。

accept

服务器程序创建并绑定了socket之后,就可以通过用accept()来等待客户建立对该socket的连接。

#include <sys/socket.h>
int accept(int socket, struct sockaddr *address, size_t *address_len);

accept()只有当有客户程序尝试连接到由socket参数指定的socket上时才返回。accept()将创建一个新socket来与该客户进行通信,将该socket描述符作为返回值。之后的读写动作都关联到该socket描述符上。参数socket所关联的套接字必须首先已经被bind绑定,而且有listen为其分配连接队列。参数address表示客户的地址,如果不关心客户的地址值可设为空指针。
- socket:侦听套接字的文件描述符。
- address:远程客户程序的网络终结点。
- address_len:address缓冲区的长度。
- 返回值:成功客户程序对应的套接字,失败返回-1。

connect

客户程序连接到服务器监听套接字的函数。

#include <sys/socket.h>
int connect(int socket, const struct sockaddr *address, size_t address_len);
  • socket:指定本地的套接字。
  • address:远程服务器程序的网络终结点。
  • address_len:address缓冲区的长度。
  • 返回值:成功返回0,失败返回-1。
    如果连接不能立刻建立,connect将阻塞到超时时间,超过超时时间连接将被放弃,连接失败。

close

可以通过close()来终止服务器与客户端的socket连接。

#include <unistd.h>
int close(int socket);

write&read

可以像读写文件一样使用write()和read()函数收发套接字数据。

send

send()同样可以发送数据,与write()不同的是,send()只能用于socket数据的发送。

#include <sys/socket.h>
int send(int socket, const void *buff, int len, int flags)
  • socket:套接字文件描述符。
  • buff:要发送的数据。
  • len:要发送的数据长度。
  • flags:一般为0。
  • 返回值:成功返回发送的字节数,失败返回-1。

recv

与send()相同,recv()也只能用于socket的数据发送。

#include <sys/socket.h>
int recv(int socket, void *buf, int len, unsigned int flags)
  • socket:套接字文件描述符。
  • buff:接收数据的缓冲区。
  • len:接收数据的缓冲区的长度。
  • flags:一般为0。
  • 返回值:成功返回接收到的字节数,失败返回-1。

sendto

sendto需要带上发送目的地的地址信息,可以用于UDP通讯的实现,TCP中也可以使用sendto()。

#include <sys/socket.h>
int sendto(int socket, const void *buff, int len, unsigned int flags, const struct sockaddr *addr_to, int addr_len)
  • socket:套接字文件描述符。
  • buff:待发送数据。
  • len:待发送数据的长度。
  • flags:一般为0。
  • addr_to:目的网络终结点地址。
  • addr _len:地址信息的长度。
  • 返回值:成功返回已发送的字节数,失败返回-1。

recvfrom

recvfrom()与sendto配套使用,实现数据的收发。

#include <sys/socket.h>
int recvfrom(int socket, const void *buff, int len, unsigned int flags, const struct sockaddr *addr_from, int addr_len);
  • socket:套接字文件描述符。
  • buff:接收数据的缓冲区。
  • len:接收数据的缓冲区的长度。
  • flags:一般为0。
  • addr_from:缓冲区用于接收远程主机的网络终结点地址。
  • addr_len:addr_from缓冲区的长度。
  • 返回值:成功返回接收到的字节数,失败返回-1。

[5]TCP通信的一般流程:

TCP通信

[6]UDP通信的一般流程:

UDP通信

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值