一、首先是服务器的建立

首先是一个信号终止程序,发信号ctrl+c终止程序,而是是初始化网络通信.

创建一个描述符负责绑定服务器和监听服务器接收客户端的消息.

socket()->sockaddr_in->bind->listen(准备就绪)

开始接收客户端消息.start()函数

首先是声明一个结构体用来存储客户端的消息,利用accept()函数来创建一个新的

描述符来接收,这里有阻塞效果,也即是说连接的时候只能一个一个的连.

然后是分离线程处理这个sockfd的连接.

pthread_create(&pid,0,pthread_deal,&sockfd1);

线程主要是先做线程的分离,然后是取得它们的sockfd描述符,把这个客户端的信息

存储到一个结构体数组中.然后是调用循环发送到各个客户端的函数,来发送消息.

当接收函数recv(sockfd,buf,sizeof(buf)) == 0 的时候,表示有客户端退出,这时

就把这个在结构体数组的相应的fd置为0

#include "server.h"
#include <sys/socket.h>
#include <arpa/inet.h>
#include <netinet/in.h> int sockfd; //服务器本身的描述符
struct User u[] = {}; //用来保存用户的信息
int size;//数组的下标,同时也是客户端的个数 void init(void) //通信准备工作
{
printf("聊天室服务器马上启动....\n");
sockfd = socket(AF_INET,SOCK_STREAM,);
if(- == sockfd)
{
perror("fail to socket");
printf("服务器故障!\n");
exit(-);
}
//准备通信地址和绑定服务器
struct sockaddr_in addr;
addr.sin_family = AF_INET;
addr.sin_port = htons(); //端口的值,转换成网络的格式
addr.sin_addr.s_addr = inet_addr("172.16.1.21");
if(- == bind(sockfd,(struct sockaddr*)&addr,sizeof(addr)))
{
perror("fail to bind");
exit(-);
}
printf("bind is ok,欢迎访问!\n");
//设置监听
if(- != listen(sockfd,))
{
printf("监听已经设置,一切准备就绪!\n");
}
} void send_msg(char *p_msg) //发送消息的函数
{
int num = ;
for(num = ;num < size;num++)
{
if(u[num].fd) //如果是有效的时候才发送
{
send(u[num].fd,p_msg,sizeof(p_msg),);
}
}
} void* pthread_deal(void* p) //线程处理函数
{
pthread_detach(pthread_self());
int fd2 = *(int*)p; //取得客户端的sockfd
u[size].fd = fd2; //放入结构体中
char name[] = {};
int res = recv(fd2,name,sizeof(name),);
if(res > )
{
strcpy(u[size].name,name);//存放用户名
}
size++;
char user[] = {};
sprintf(user,"%s悄悄的进来了!(*^__^*) 嘻嘻……\n",name);
send_msg(user);
while()
{
if(recv(fd2,name,sizeof(name),) == ) /*返回0表示有客户端退出*/
{
u[size-].fd = ; //把退出的客户端的结构描述符置换成0
}
}
} void start(void)
{
printf("success to start server,let's go!\n");
while()
{
struct sockaddr_in client;//存储接收到的客户端的信息
socklen_t length = sizeof(client);
//接收客户端的信息,会有阻塞效果,sockfd1标记客户端
int sockfd1 = accept(sockfd,(struct sockaddr*)&client,&length);
if(sockfd1 == -)
{
perror("fail to accept!");
continue; //继续连接
}
printf("%s连接上来了\n",inet_ntoa(client.sin_addr));
/*连接成功之后,就启动线程*/
pthread_t pid;//线程id
pthread_create(&pid,,pthread_deal,&sockfd1);
}
} void sig_exit(int signo ) //子定义信号关闭服务器函数
{
close(sockfd);//关闭服务器端口
printf("服务器成功关闭!\n");
exit();
}
int main(void)
{
printf("按ctrl+c关闭聊天室服务器!\n");
signal(SIGINT,sig_exit);
init();//初始化,服务器通信准备工作
start();//启动服务(开始处理聊天信息)
return ;
}

2.客户端的编写.

Linux网络编程(多人在线聊天系统)的更多相关文章

  1. 网络编程懒人入门(九):通俗讲解,有了IP地址,为何还要用MAC地址?

    1.前言 标题虽然是为了解释有了 IP 地址,为什么还要用 MAC 地址,但是本文的重点在于理解为什么要有 IP 这样的东西.本文对读者的定位是知道 MAC 地址是什么,IP 地址是什么. (本文同步 ...

  2. 网络编程懒人入门(八):手把手教你写基于TCP的Socket长连接

    本文原作者:“水晶虾饺”,原文由“玉刚说”写作平台提供写作赞助,原文版权归“玉刚说”微信公众号所有,即时通讯网收录时有改动. 1.引言 好多小白初次接触即时通讯(比如:IM或者消息推送应用)时,总是不 ...

  3. 网络编程懒人入门(六):深入浅出,全面理解HTTP协议

    本文引用了自简书作者“涤生_Woo”的文章,内容有删减,感谢原作者的分享. 1.前言 HTTP(全称超文本传输协议,英文全称HyperText Transfer Protocol)是互联网上应用最为广 ...

  4. 【深入浅出Linux网络编程】 "开篇 -- 知其然,知其所以然"

    [深入浅出Linux网络编程]是一个连载博客,内容源于本人的工作经验,旨在给读者提供靠谱高效的学习途径,不必在零散的互联网资源中浪费精力,快速的掌握Linux网络编程. 连载包含4篇,会陆续编写发出, ...

  5. Linux网络编程&内核学习

    c语言: 基础篇 1.<写给大家看的C语言书(第2版)> 原书名: Absolute Beginner's Guide to C (2nd Edition) 原出版社: Sams 作者: ...

  6. Linux网络编程入门 (转载)

    (一)Linux网络编程--网络知识介绍 Linux网络编程--网络知识介绍客户端和服务端         网络程序和普通的程序有一个最大的区别是网络程序是由两个部分组成的--客户端和服务器端. 客户 ...

  7. Linux网络编程必看书籍推荐

    首先要说讲述计算机网络和TCP/IP的书很多. 先要学习网络知识才谈得上编程 讲述计算机网络的最经典的当属Andrew S.Tanenbaum的<计算机网络>第五版,这本书难易适中. &l ...

  8. [转] - Linux网络编程 -- 网络知识介绍

    (一)Linux网络编程--网络知识介绍 Linux网络编程--网络知识介绍客户端和服务端         网络程序和普通的程序有一个最大的区别是网络程序是由两个部分组成的--客户端和服务器端. 客户 ...

  9. 【转】Linux网络编程入门

    (一)Linux网络编程--网络知识介绍 Linux网络编程--网络知识介绍客户端和服务端         网络程序和普通的程序有一个最大的区别是网络程序是由两个部分组成的--客户端和服务器端. 客户 ...

随机推荐

  1. 冰球项目日志3-yjw

    小组讨论 今天大家讨论了之前各自想的方案的问题,基本确定了寻找击球点的方案,以及击球手运动轨迹规划的方案,这里我只是简单的说下我们的击球点的确定方案. 击球策略方案 方案分析 首先我们建立平面在直角坐 ...

  2. 一张图看懂单机/集群/热备/磁盘阵列(RAID)

  3. 解决首次访问jenkins,输入默认密码之后,一直卡住问题

    简介   安装系统:centos6.5 安装方式:在官网中下载jenkins.war,放到tomcat根目录下的webapps中,启动tomcat(还有一种yum在线安装的方式) 1.首次访问,出现如 ...

  4. python unicode转中文及转换默认编码

    一. 在爬虫抓取网页信息时常需要将类似"\u4eba\u751f\u82e6\u77ed\uff0cpy\u662f\u5cb8"转换为中文,实际上这是unicode的中文编码.可 ...

  5. python 基本语法

    第一个python程序 打开Sublime Text -->输出 print"Hello World" -->保存为frist.py -->打开命令行运行,运行p ...

  6. CentOS 7 配置静态IP

    1.查看MAC地址 2.修改/etc/sysconfig/network-scripts/ifcfg-[第一步中红框内的文字] 3.添加和修改内容如下: 4.修改/etc/resolv.conf 5. ...

  7. Oracle表空间,用户,用户授权

    一:Oracle表空间 1,Oracle表空间与SQL Server文件组对比 SQL Server的文件组(文件组包括若干MDF,NDF数据文件)对我们来说并不陌生,前段时间我在博客“怎样玩转千万级 ...

  8. Joomla软件功能介绍与开源程序大比拼Joomla,wordpress,Drupal哪个好?

    Joomla 软件功能介绍:    Joomla!是一套在国外相当知名的内容管理系统 (Content Management System, CMS),它属于Portal(企业入口网站)类型,顾名思义 ...

  9. Windows Store App JavaScript 开发:WinJS库控件

    在介绍了如何使用标准的HTML控件以及WinJS库中提供的新控件之后,下面来着重介绍WinJS库中几种常用的控件. (1)ListView控件 在开发Windows应用商店应用时可以使用ListVie ...

  10. 夕甲甲——孔乙己之C++版

    欧欧匹代码的格局,是和别的编程模式不同的:首先要有一个构造函数:基类里只定义了函数的形式,可以随时通过派生增加不同的实现.那些程序员们,每每学会了继承和多态,便可以接一个项目,——这是十年前的事,现在 ...