利用套接字实现 CS 模型

这个示例展示了如何使用C语言实现一个简单的TCP服务器,它接收客户端发送的文本,将所有字符转换为大写,然后回送给客户端。服务器监听8888端口,客户端通过连接该端口进行交互。程序涉及套接字编程,包括socket创建、bind、listen、accept以及read和write操作。
摘要由CSDN通过智能技术生成

例子:大写转小写。
注意:代码都是运行在Linux内核中。
服务器端:

#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <stdio.h>
#include <arpa/inet.h>
#include <ctype.h>
int main()
{
 // 1、创建套接字
 int lfd = socket(AF_INET, SOCK_STREAM, 0);
 // 2、绑定IP和端口号
 struct sockaddr_in server_addr; // 创建结构体
 server_addr.sin_family = AF_INET; // 指定IPv4
 server_addr.sin_port = htons(8888); // 将端口号转换为网络字节序
 server_addr.sin_addr.s_addr = htonl(INADDR_ANY); // 将本地任意IP转为网络字节序
 bind(lfd, (struct sockaddr*)&server_addr, sizeof(server_addr)); // 绑定,注意强转
// 3、监听
 listen(lfd,128); // 上限128
 // 4、阻塞等待客户端链接(获得一个新的指向客户端文件描述符)
struct sockaddr_in client_addr; // 传入参数:要先定义,然后传入
socklen_t client_addr_len = sizeof(client_addr); // 传入传出参数:要先定义赋值,然后传入
int cfd = accept(lfd, (struct sockaddr*)&client_addr, &client_addr_len); // 指向客户端
// 输出客户端信息
 char ip[256] = {0}; // 用于存储IP字符串
 printf("client IP: %s 端口号: %d\n", 
 inet_ntop(AF_INET, &client_addr.sin_addr.s_addr, ip, sizeof(ip)),
 ntohs(client_addr.sin_port) ); // 2个函数的返回值分别是IP和端口号
 // 以下为通信
 char buf[256];
 while(1) // 实现循环操作
{
 // 读取客户端传来的内容
 int n = read(cfd, buf, sizeof(buf)); // 返回值是读到的字节数(字母个数)
 // 转换字母
 for(int i = 0; i < n; i++)
 buf[i] = toupper( buf[i] ); 
 // 写回给客户端
 write(cfd, buf, n);
 }
 //关闭
 close(lfd);
 close(cfd);
 return 0;
}

客户端:

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <string.h>
int main()
{
 // 创建客户端socket
 int cfd = socket(AF_INET, SOCK_STREAM, 0);
 // 客户端应该绑定bind自己的IP和端口,但也可以不绑定,系统会帮助做“隐式绑定”
 // 注意:服务器可以做隐式绑定吗?
// 答: 不可以,因为隐式绑定,服务器的IP和端口不固定,客户端不知道该连接哪
 // 链接服务器
 struct sockaddr_in server_addr; // 因为要链接服务器,存储的服务器的IP地址和端口号
 // 指定服务器的地址信息
 server_addr.sin_family = AF_INET;
 server_addr.sin_port = htons(8888); 
 inet_pton(AF_INET, "127.0.0.1", &server_addr.sin_addr.s_addr); // 转 网络字节序 
socklen_t addrlen = sizeof(server_addr); // 指定服务器的地址长度
 connect(cfd, (struct sockaddr*)&server_addr, addrlen); // 链接服务器
 char buf[256];
 while(1)
 {
 // 向服务器传数据
 fgets(buf, sizeof(buf), stdin); // 从键盘输入,存入buf
 // 注意:fgets 特性,一直接收键盘输入,以回车作为结尾,然后自动给加\0
 // 举例 hello 经过fgets 存入buf的是 “hello\n\o”
 write(cfd, buf, strlen(buf)); // 因此,此处用strlen,而不是sizeof
 // 服务器处理后,客户端读取数据
 int n = read(cfd, buf, sizeof(buf));
 // 写入屏幕
 write(STDOUT_FILENO, buf, n);
 }
 close(cfd);
 return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值