当前位置: 首页 > news >正文

Linux C 基于tcp和epoll在线聊天室

基于tcp和epoll在线聊天室

  • 说明
  • 服务端代码

说明

  服务端:实现了验证用户是否已经存在(支持最大64用户连接)支持广播用户进入退出聊天室以及用户聊天内容。
  这里只提供里服务端代码,如果想要看客户端代码点击这里。

服务端代码

#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <string.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include<sys/types.h>
#include<sys/socket.h>
#include <arpa/inet.h>
#include <time.h>
#include <sys/epoll.h>typedef struct sockaddr  SA;
typedef struct sockaddr_in  SIN;
#define MAXBACKLOG   100int Socket(int domain,int type,int protocol);
int Bind(int sockfd,struct sockaddr * my_addr,int addrlen);
int Listen(int s,int backlog);
int Accept(int s,struct sockaddr * addr,int * addrlen);
int is_exist(char * username);
void broadcast(char *r,char *n);char Userlist[64][20] = {0};
int Userfdlist[64] = {0};//./app 192.168.5.166  8888
int main(int argc,char *argv[])
{	int opt = 1;//建立监听套接字int socketfd = Socket(AF_INET,SOCK_STREAM,0);//需要进行重用地址及其端口号setsockopt(socketfd,SOL_SOCKET,SO_REUSEADDR,&opt,sizeof(opt));//绑定信息编写服务器信息SIN   serverinfo;serverinfo.sin_family =AF_INET;serverinfo.sin_port   =htons(atoi(argv[2])); serverinfo.sin_addr.s_addr=  inet_addr(argv[1]);int addrlen = sizeof(SIN);Bind(socketfd,(SA*)&serverinfo,addrlen);//监听Listen(socketfd,MAXBACKLOG);//epoll创建根节点int epollfd = epoll_create(1024);//添加socketfd文件描述符至内核 红黑树struct epoll_event event;event.events = EPOLLIN;			//事件成员event.data.fd = socketfd;		//数据epoll_ctl(epollfd,EPOLL_CTL_ADD,socketfd, &event);//读写while(1){struct epoll_event events[10];int count = epoll_wait(epollfd,events,10,-1);for(int i = 0; i< count;i++){if(events[i].events == EPOLLIN){if(events[i].data.fd == socketfd){//wait client connectSIN clientinfo;struct epoll_event event;int  clientaddrlen =sizeof(SA);int newfd = Accept(socketfd,(SA*)&clientinfo,&clientaddrlen);printf("客户端地址:%s 端口号:%d\n",inet_ntoa(clientinfo.sin_addr),ntohs(clientinfo.sin_port));//read usernamechar namebuff[20];read(newfd,namebuff,sizeof(namebuff));if(is_exist(namebuff)){write(newfd,"已存在",sizeof("已存在"));close(newfd);}else{//put newfd into Red-Black Treeevent.events = EPOLLIN;			//事件成员event.data.fd = newfd;			//数据epoll_ctl(epollfd,EPOLL_CTL_ADD,newfd, &event);write(newfd,"登录成功",sizeof("登录成功"));	//save userfd & usernamefor(int j=0;j<64;j++)if(strlen(Userlist[j])==0){Userfdlist[j]=event.data.fd;strcpy(Userlist[j],namebuff);break;}	char r[50];sprintf(r,"%s %s",namebuff,"进入聊天室");printf("%s\n",r);broadcast(r,namebuff);}}else{//readchar readbuff[512] = {0};int len = read(events[i].data.fd,readbuff,sizeof(readbuff));//get name and poschar namebuff[20] = {0};int key = 0;for(int i=0;i<10;i++)if(strstr(readbuff,Userlist[i])){strcpy(namebuff,Userlist[i]);key=i;break;}if(len > 0 && strlen(readbuff)!=0){printf("%s\n",readbuff);broadcast(readbuff,namebuff);if(strstr(readbuff,"退出")){strcpy(Userlist[key],"\0");Userfdlist[key] = 0;epoll_ctl(epollfd,EPOLL_CTL_DEL,events[i].data.fd,NULL);close(events[i].data.fd);}}else if(len <= 0){epoll_ctl(epollfd,EPOLL_CTL_DEL,events[i].data.fd,NULL);close(events[i].data.fd);}}}}}//关闭close(socketfd);return 0;
}
int is_exist(char * username)
{for(int i = 0 ; i < 10; i++)if(strcmp(username,Userlist[i]) == 0)return 1;return 0;
}
void broadcast(char *r,char *n)
{for(int i=0 ; i<64 ;i++)//if it is a user and not himselfif(strcmp(Userlist[i],n)!=0 && strlen(Userlist[i])!=0)write(Userfdlist[i],r,strlen(r));
}
int Socket(int domain,int type,int protocol)
{int socketFd = socket(domain,type,protocol);if(socketFd == -1){perror("socket");exit(1);}return socketFd;
}
int Bind(int sockfd,struct sockaddr * my_addr,int addrlen)
{int val = bind(sockfd,my_addr,addrlen);if(val){perror("bind");exit(1);}return 0;
}
int Listen(int s,int backlog)
{int val = listen(s,backlog);if(val == -1){perror("listen");exit(1);}return val;
}
int Accept(int s,struct sockaddr * addr,int * addrlen)
{int NEWfd = accept(s,addr,addrlen);if(NEWfd == -1){perror("listen");exit(1);}return NEWfd;
}

相关文章:

Linux C 基于tcp和epoll在线聊天室

基于tcp和epoll在线聊天室 说明服务端代码 说明 服务端&#xff1a;实现了验证用户是否已经存在&#xff08;支持最大64用户连接&#xff09;支持广播用户进入退出聊天室以及用户聊天内容。   这里只提供里服务端代码&#xff0c;如果想要看客户端代码点击这里。 服务端代码…...

为什么要隐藏id地址?使用IP代理技术可以实现吗?

随着网络技术的不断发展&#xff0c;越来越多的人开始意识到保护个人隐私的重要性。其中&#xff0c;隐藏自己的IP地址已经成为了一种常见的保护措施。那么&#xff0c;为什么要隐藏IP地址&#xff1f;使用IP代理技术可以实现吗&#xff1f;下面就一起来探讨这些问题。 首先&am…...

前端(HTML + CSS + JS)

文章目录 一、HTML1. 概念&#xff08;1&#xff09;HTML 文件基本结构&#xff08;2&#xff09;HTML代码框架 2. 、HTML常见标签 二、CSS1. CSS基本语法规范2. 用法&#xff08;1&#xff09; 引用方式&#xff08;2&#xff09;选择器&#xff08;3&#xff09;常用元素属性…...

12 要素 12 Factor

I. 基准代码 一份基准代码&#xff0c;多份部署 一个应用&#xff0c;一个基准代码git仓库&#xff0c;多个环境版本部署&#xff08;prod&#xff0c;staging&#xff0c;develop&#xff09; II. 依赖 显式声明依赖关系 docker的dockerfile&#xff0c;php的composer.jso…...

十大排序之冒泡排序与快速排序(详解)

文章目录 &#x1f412;个人主页&#x1f3c5;算法思维框架&#x1f4d6;前言&#xff1a; &#x1f380;冒泡排序 时间复杂度O(n^2)&#x1f387;1. 算法步骤思想&#x1f387;2.动画实现&#x1f387; 3.代码实现&#x1f387;4.代码优化&#xff08;添加标志量&#xff09; …...

【SpringBoot篇】阿里云OSS—存储文件的利器

文章目录 &#x1f339;什么是阿里云OSS⭐阿里云OSS的优点 &#x1f3f3;️‍&#x1f308;为什么要使用云服务OSS&#x1f384;使用步骤⭐OSS开通⭐参考官方SDK &#x1f354;编写代码⭐上传文件 &#x1f339;综合案例 &#x1f339;什么是阿里云OSS 阿里云对象存储&#xf…...

Leetcode—58.最后一个单词的长度【简单】

2023每日刷题&#xff08;四十&#xff09; Leetcode—58.最后一个单词的长度 实现代码 int lengthOfLastWord(char* s) {int len strlen(s);int left 0, right 0;if(len 1) {return 1;}while(right < len) {if(right 1 < len) {if(s[right] && s[righ…...

Apach Ozone部署

前言 最近由于工作需要&#xff0c;要部署一套ozone。我自己对hadoop这套体系不是很熟悉&#xff0c;所以过程磕磕碰碰&#xff0c;好不容易勉强搭起来&#xff0c;所以记录一下部署方式 准备 三台主机&#xff0c;主机均已安装jdk、hdfs&#xff0c;相关的安装配置就不另外写…...

【nlp】3.2 Transformer论文复现:1. 输入部分(文本嵌入层和位置编码器)

Transformer论文复现:输入部分(文本嵌入层和位置编码器) 1 输入复现1.1 文本嵌入层1.1.1 文本嵌入层的作用1.1.2 文本嵌入层的代码实现1.1.3 文本嵌入层中的注意事项1.2 位置编码器1.2.1 位置编码器的作用1.2.2 位置编码器的代码实现1.2.3 位置编码器中的注意事项1 输入复现…...

自动化部署 / 扩容openGauss —— Ansible for openGauss

前言 大家好&#xff0c;今天我们为大家推荐一套基于 Ansible 开发的&#xff0c;自动化部署及扩容 openGauss 的脚本工具&#xff1a;Ansible for openGauss&#xff08;以下简称 AFO&#xff09;。 通过AFO&#xff0c;我们只需简单修改一些配置文件&#xff0c;即可快速部署…...

Go 实现网络代理

使用 Go 语言开发网络代理服务可以通过以下步骤完成。这里&#xff0c;我们将使用 golang.org/x/net/proxy 包来创建一个简单的 SOCKS5 代理服务作为示例。 步骤 1. 安装 golang.org/x/net/proxy 包 使用以下命令安装 golang.org/x/net 包&#xff0c;该包包含 proxy 子包&am…...

Redis报错:JedisConnectionException: Could not get a resource from the pool

1、问题描述&#xff1a; redis.clients.jedis.exceptions.JedisConnectionException: Could not get a resource from the pool 2、简要分析&#xff1a; redis.clients.util.Pool.getResource会从JedisPool实例池中返回一个可用的redis连接。分析源码可知JedisPool 继承了 r…...

【广州华锐互动】Web3D云展编辑器能为展览行业带来哪些便利?

在数字时代中&#xff0c;传统的展览方式正在被全新的技术和工具所颠覆。其中&#xff0c;最具有革新意义的就是Web3D云展编辑器。这种编辑器以其强大的功能和灵活的应用&#xff0c;正在为展览设计带来革命性的变化。 广州华锐互动开发的Web3D云展编辑器是一种专门用于创建、编…...

Vue项目实战之一----实现分类弹框效果

效果图 实现 <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>Title</title><script src"js/vue.js"></script><!-- 引入样式 --><link rel"stylesheet&qu…...

Vue解析器

解析器本质上是一个状态机。但我们也曾提到&#xff0c;正则表达式其实也是一个状态机。因此在编写 parser 的时候&#xff0c;利用正则表达式能够让我们少写不少代码。本章我们将更多地利用正则表达式来实现 HTML 解析器。另外&#xff0c;一个完善的 HTML 解析器远比想象的要…...

Spring Cloud 版本升级遇坑记:OpenFeignClient与Gateway的恩怨情仇

Spring Cloud 版本升级遇坑记&#xff1a;OpenFeignClient与Gateway的恩怨情仇 近日&#xff0c;在对项目中的 Spring Boot、Spring Cloud 以及 Spring Cloud Alibaba 进行版本升级时&#xff0c;遭遇了一个令人头疼的问题&#xff1a;Spring Cloud Gateway 在运行时一直卡住&a…...

面试:Docker相关问题

文章目录 请解释一下什么是 Docker&#xff0c;以及它在云环境中的应用请简述Docker和LXC的区别什么是Docker Compose&#xff1f;请简述其作用和使用场景在使用Docker时&#xff0c;如何为容器创建一个可访问的网络当一个Docker容器运行异常时&#xff0c;如何通过Docker命令查…...

移动端浏览器 jquery 获取 pdf blob文件流 预览pdf

最近遇到一个需求&#xff0c;一个古早的移动端 juery 项目要求做一个页面&#xff0c;从接口获取 pdf 文件流&#xff0c;然后预览出来 这里使用第三方工具&#xff1a;pdf.js 代码如下&#xff1a; // 引入相关文件<script src"../js/pdf.js" type"text…...

Redis并发问题解决方案

目录 前言 1.分布式锁 1.基于单个节点 2.基于多个节点 3.watch(乐观锁) 2.原子操作 1.单命令操作 2.Lua 脚本(多命令操作) 3.事务 1.执行步骤 2.错误处理 3.崩溃处理 总结 前言 在多个客户端并发访问Redis的时候&#xff0c;虽然Redis是单线程执行指令&#xff…...

读取两个文件夹里不同名的文件,处理映射不对应的文件

解决方案&#xff1a;读取两个文件夹里不同名的文件&#xff0c;处理映射不对应的文件 # -*- coding: utf-8 -*- import ospath1 r/home/ubuntu/data/yoloData/images/train2017 path2 r/home/ubuntu/data/yoloData/labels/train2017def read_all_file_name():file_path ./t…...

2026最权威的十大降AI率助手解析与推荐

Ai论文网站排名&#xff08;开题报告、文献综述、降aigc率、降重综合对比&#xff09; TOP1. 千笔AI TOP2. aipasspaper TOP3. 清北论文 TOP4. 豆包 TOP5. kimi TOP6. deepseek 如今&#xff0c;好多 AI 生成内容检测工具越来越常见&#xff0c;致使原创文本要是带有明显…...

Docker+Python+openGauss:5分钟搭建你的第一个数据库Web应用原型

DockerPythonopenGauss&#xff1a;从零构建学生成绩管理系统原型 在当今快速迭代的软件开发环境中&#xff0c;能够迅速验证想法并构建最小可行产品(MVP)的能力变得至关重要。对于全栈开发初学者而言&#xff0c;掌握如何将数据库、后端服务和前端展示无缝衔接是一项基础但关键…...

NVIDIA Llama Nemotron Ultra:开源推理模型的技术突破与应用

1. NVIDIA Llama Nemotron Ultra&#xff1a;重新定义开源推理模型的新标杆作为一名长期关注AI技术发展的从业者&#xff0c;我最近深度测试了NVIDIA最新发布的Llama Nemotron Ultra模型。这款开源推理模型在科学推理、编程和数学三大领域的表现确实令人惊艳&#xff0c;特别是…...

企业大模型私有化部署完全指南:数据不出门,智能照样顶

别再让核心数据裸奔了&#xff01;三步搭建你自己的AI能力中心&#xff0c;成本不到云服务的一半引言&#xff1a;为什么2026年每家企业都该有个“私人大模型”&#xff1f;你有没有遇到过这种情况&#xff1a;想让AI帮忙分析公司上季度的销售数据&#xff0c;但又怕把Excel上传…...

【C# 14 原生AOT实战白皮书】:Dify客户端部署性能跃升3.7倍的5大关键配置与避坑清单

第一章&#xff1a;C# 14 原生AOT部署Dify客户端对比评测报告总览本章聚焦于使用 C# 14 全新原生 AOT&#xff08;Ahead-of-Time&#xff09;编译能力构建并部署 Dify 官方 API 客户端的实践路径与性能对比。Dify 作为开源 LLM 应用开发平台&#xff0c;其 RESTful 接口广泛用于…...

Inspirit Capital将收购Kaplan Languages Group

专注于企业分拆业务投资的Inspirit Capital欣然宣布&#xff0c;计划从Kaplan手中收购全球领先的语言教育平台KLG Kaplan Languages Group (“KLG”)。本次出售的所有条件均已达成&#xff0c;预计交易将于5月1日完成。 KLG旗下拥有Kaplan International Languages、Alpadia L…...

Cadence Virtuoso 新手避坑指南:从原理图到版图,手把手搞定 AMI 0.6u 工艺下的 MOS 管仿真

Cadence Virtuoso 新手避坑指南&#xff1a;从原理图到版图&#xff0c;手把手搞定 AMI 0.6u 工艺下的 MOS 管仿真 第一次打开 Cadence Virtuoso 时&#xff0c;复杂的界面和密密麻麻的菜单栏让不少集成电路专业的学生望而生畏。尤其是当教授要求用 AMI 0.6u 工艺完成 MOS 管仿…...

别再乱打拍了!从亚稳态到异步FIFO,手把手教你搞定FPGA跨时钟域信号处理

从亚稳态到异步FIFO&#xff1a;FPGA跨时钟域信号处理实战指南 在FPGA和数字IC设计中&#xff0c;跨时钟域信号处理是一个永恒的话题。每当项目进度紧张、调试压力增大时&#xff0c;工程师们最不愿看到的就是时序报告里那些令人头疼的违例警告。我曾在一个高速数据采集项目中…...

OpenSpec 技术架构深度解析:规范驱动 AI 编程的工程化实践

随着大语言模型(LLM)能力的飞跃式提升,AI 编程助手已经从概念走向生产。Claude Code、Cursor、Copilot 等工具让开发者能够通过自然语言指令快速生成代码,极大地提升了开发效率。然而,这种"氛围编程"(Vibe Coding)模式在带来便利的同时,也暴露出严重的工程化…...

Layui-admin后台管理系统:3倍开发效率的企业级解决方案

Layui-admin后台管理系统&#xff1a;3倍开发效率的企业级解决方案 【免费下载链接】Layui-admin 一个现成的 LayuiVue的后台系统模板&#xff0c;开箱即用 项目地址: https://gitcode.com/gh_mirrors/layu/Layui-admin 在当今快速迭代的商业环境中&#xff0c;企业后台…...