分享了这么多进程和网络通信的知识点,为了能让大家将这些知识串起来,今天我将在linux下开发一个多进程和网络通信结合小项目.
项目的主要内容为:
(1)创建一个8080端口,使用tcp协议通信的服务端,用于监听客户端发来的消息并显示在终端上;
(2)创建一个多进程的客户端程序,其中子进程用于连接到服务器并发送消息,父进程大家可以添加自己想要添加的业务.
话不多说直接上代码:
服务端程序
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>
int main() {
int server_sock;
struct sockaddr_in server_addr, client_addr;
socklen_t socklen = sizeof(client_addr);
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = INADDR_ANY;
server_addr.sin_port = htons(8080);
server_sock = socket(AF_INET, SOCK_STREAM, 0);
if (server_sock == -1) {
perror("socket error!");
exit(1);
}
if (bind(server_sock, (struct sockaddr*)&server_addr, sizeof(server_addr)) == -1) {
perror("bind error!");
exit(1);
}
if (listen(server_sock, 3) == -1) {
perror("listen error!");
exit(1);
}
printf("正在监听8080端口!\n");
while (1) {
int new_sock = accept(server_sock, (struct sockaddr*)&client_addr, &socklen);
if (new_sock == -1) {
perror("accept error!");
exit(1);
}
char message[1024];
ssize_t bytesRead = read(new_sock, message, sizeof(message) - 1); // 减去一个字节是为了确保有空间存放终止字符 '\0'。
if (bytesRead == -1) {
perror("read error!");
close(new_sock); // 关闭新套接字句柄,避免资源泄漏。
continue; // 继续等待下一个连接。
}
message[bytesRead] = '\0'; // 添加终止字符。
printf("[%d]:%s", getpid(), message);
close(new_sock); // 关闭新套接字句柄,释放资源。
}
}
客户端程序
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
int main() {
int sock;
struct sockaddr_in server_addr;
char message[1024];
// 创建套接字
sock = socket(AF_INET, SOCK_STREAM, 0);
if (sock == -1) {
perror("socket error!");
exit(EXIT_FAILURE);
}
// 设置服务器地址信息
server_addr.sin_family = AF_INET;
server_addr.sin_addr.s_addr = INADDR_ANY; // 服务器IP地址,此处使用本地回环地址
server_addr.sin_port = htons(8080); // 服务器端口号
pid_t pid = fork();
if (pid < 0) {
perror("fork error!");
exit(EXIT_FAILURE);
} else if (pid == 0) { // 子进程
// 连接到服务器
if (connect(sock, (struct sockaddr*)&server_addr, sizeof(server_addr)) == -1) {
perror("connect error!");
exit(EXIT_FAILURE);
}
printf("已连接到服务器!\n");
// 发送消息给服务器
printf("请输入要发送的消息:");
fgets(message, sizeof(message), stdin); // 从标准输入读取消息,并包含换行符
write(sock, message, strlen(message) );
printf("消息已发送给服务器!\n");
close(sock); // 在子进程中不关闭套接字,因为父进程会关闭它。
exit(EXIT_SUCCESS); // 子进程结束时退出。
} else { // 父进程 在此可以添加其他主进程业务
wait(&pid); // 等待子进程结束。
close(sock); // 父进程关闭套接字。
}
return 0;
}
在终端分别运行这两个程序,得到结果:
客户端:
服务端: