UNIX网络编程3:基本TCP套接字编程

时间:2022-01-10 01:45:07

1. 基本TCP客户/服务器程序的套接字函数

UNIX网络编程3:基本TCP套接字编程

2. socket函数:指定期望的通信协议类型

#include <sys/socket.h>
int socket(int family, int type, int protocal);//若成功则返回非负描述符,若失败则返回-1

socket函数成功时返回的为套接字描述符(socket descriptor,简称sockfd)

socket函数的family常值:

UNIX网络编程3:基本TCP套接字编程
socket函数的type常值:

UNIX网络编程3:基本TCP套接字编程

socket函数的protocol常值:

UNIX网络编程3:基本TCP套接字编程

family和type的有效组合(标记为是的也是有效组合,但没有找到合适的缩略词)

UNIX网络编程3:基本TCP套接字编程

3. connect函数

TCP客户用connect函数来建立与TCP服务器的连接,如果是TCP套接字,调用connect函数将引发三次握手过程,并且仅在连接成功或者出错时才返回。

#include <sys/socket.h>
int connect(int sockfd, const struct sockaddr *servaddr, socklen_t addrlen);

4. bind函数

bind函数把一个本地协议地址赋予一个套接字,对于网际网协议,协议地址是32位的IPv4地址或128位的IPv6地址与16位的TCP或UDP端口号的组合。调用bind函数可以指定IP地址或者端口号,可以两者都指定,也可两者都不指定。

#include <sys/socket.h>
int bind(int sockfd, const struct sockaddr * servaddr, socklen_t addrlen); //成功则返回0,出错则返回-1

5. listen函数

仅由TCP服务器调用,将一个未连接的套接字转换成一个被动套接字,指示内核应接受指向该套接字的连接请求。

#include <sys/socket.h>
//backlog规定应为相应套接字排队的最大连接个数
int listen(int sockfd, int backlog);//若成功则返回0,出错则返回-1
内核为任何一个监听套接字维护两个队列:未完成连接队列(还没有完成三次握手)和已完成连接队列。两队列之和不超过backlog
UNIX网络编程3:基本TCP套接字编程

6. accept函数

由TCP服务器调用,用于从已完成连接队列队头返回一个已完成连接,如果已完成连接为空,那么进程被投入睡眠。

#include<sys/socket.h>
//sockfd为监听套接字描述符,若accept成功,返回的是已连接套接字描述符
//cliaddr和addrlen用来返回已连接的对端进程(客户)的协议地址及该地址的长度,如果对返回客户地址不感兴趣,可以将这两个指针置为空指针
int accept(int sockfd, struct sockaddr *cliaddr, socklen_t *addrlen);//若成功则返回非负描述符(已连接套接字描述符),若失败则返回-1
7. fork和exec函数

fork函数是unix派生新进程的唯一方法。

#include <unistd.h>
pid_t fork(void); //调用fork函数一次,返回两次,在父进程中返回新派生进程的进程ID,在子进程中返回0。若出错返回-1。

父进程和子进程:
  • 任何一个子进程只有一个父进程,子进程总是可以通过调用getppid获得父进程的进程ID。
  • 父进程可以有很多子进程,但是无法获得子进程的进程ID,只能通过跟踪fork函数的返回值来记录子进程ID
  • 父进程中调用fork之前的所有描述符在fork返回之后由子进程共享
fork函数的两种用法:
  • 一个进程创建自身的副本,这样每个副本可以同时处理不同操作
  • 一个进程想要执行另一个程序:一个进程调用fork创建自身的副本,然后子进程调用exec把自身替换成新的程序
exec函数:有6个
UNIX网络编程3:基本TCP套接字编程UNIX网络编程3:基本TCP套接字编程

8. close函数 close函数用来关闭套接字,并终止TCP连接
#include <unistd.h>
int close(int sockfd);//若成功则返回0,出错则返回-1
9. getsockname和getpeername函数
返回与某个套接字关联的本地协议地址、外地协议地址。
#include <sys/socket.h>
//成功则返回0,出错则返回-1
int getsockname(int sockfd, struct sockaddr *localaddr, socklen_t * addrlen);
int getpeername(int sockfd, struct sockaddr *peeraddr, socklen_t * addrlen);