Linux/Unix系统一切都是文件

Linux系统中,存在一个虚拟文件系统VFS,把一切实体视为文件,包括普通文件、音视频、输入输出设备等。这样,操作系统可以可以提供统一的接口来操作任何实体。每个“文件”创建后,都有一个文件描述符(File Describer),文件描述符是一个正整数,操作系统通过文件描述符对有关文件进行操作。一般来说,每次调用创建文件的函数,都会返回一个FD,若果创建失败,则会返回负数,一般是-1 。这是了解Socket编程的基础。

Socket的理解

数据链路层、网络层、传输层的协议都是在操作系统的内核中完成的,应用层的编写是用户自定义完成的。用户应用的应用层协议需要下层协议提供的服务,而前三者的调用是Linux系统的一组系统调用,需要使用Linux系统提供的API。Socket是实现上述系统调用的API的总称

socket通信步骤

  • 创建 int scoket(int domain, int type, int protocol)
  • 绑定socket与socket地址:int bind(int socketfd, const struct sockaddr* my_addr, scoklen_t addrlen)
  • 监听socket,用于服务器:int listen(int sockfd, int backlog)
  • 接受listen队列的一个连接,用于服务器:int accept(int sockfd, struct sockaddr* addr, socklen_t *addrlen)
  • 发起连接,用于客户端:int connect(int sockfd, const struct sockaddr* serv_addr, socklen_t addrlen)
  • 关闭连接:int close(int fd)

Tcp数据读写

  • 读取Tcp数据:ssize_t recv(int sockfd, void* buf, size_t len, int flags),如果返回数据的长度小于期望的长度,则多次读
  • 写入数据:ssize_t send(int sockfd, const void* buf, size_t len, int flags)

代码编写

开发环境:Ubuntu 18.04 LTS
编译器: gcc 7.3
处理逻辑:服务器开启,如果有客户端链接,则接受连接并返回一个数据,之后关闭客户端的连接。

服务器模型

#include <sys/socket.h>
#include <stdlib.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <time.h>
#include <netinet/in.h>
#include <stdio.h>int main(int argc, char* argv[]) {if(2 != argc) {printf(" Usage: %s <port of server>\n", argv[0]);return -1;}int port = atoi(argv[1]);if(port < 0) {printf("\nError: port error\n");return -1;}int socketfd = 0;socketfd = socket(AF_INET, SOCK_STREAM, 0);if(socketfd < 0) {printf("\nError: can not create socket\n");return -1;}struct sockaddr_in serv_addr;char sendBuffer[1025];bzero(&serv_addr, sizeof(serv_addr));bzero(sendBuffer, sizeof(sendBuffer));serv_addr.sin_family = AF_INET;serv_addr.sin_port = htons(port);serv_addr.sin_addr.s_addr = htonl(INADDR_ANY); if(bind(socketfd, (struct sockaddr*)&serv_addr, sizeof(serv_addr)) < 0) {printf("\nError: can not bind socket on port %d\n", port);return -1;}if(listen(socketfd, 10) < 0) {printf("\nError: can not listen on port %d with backlog = 5\n", port);return -1;}time_t ticks;int connfd;while(1) {connfd = accept(socketfd, (struct sockaddr*)NULL, NULL);snprintf(sendBuffer, sizeof(sendBuffer), "%.24s\r\n", ctime(&ticks));send(connfd, sendBuffer, sizeof(sendBuffer), 0);close(connfd);sleep(1);}return 0;
}

客户端模型

#include <sys/types.h>
#include <sys/socket.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <arpa/inet.h>
#include <netinet/in.h>
#include <string.h>int main(int argc, char* argv[]) {if(3 != argc) {printf(" Usage: %s <ip of server> <port of server>\n", argv[0]);return -1;}struct sockaddr_in serv_addr;bzero(&serv_addr, sizeof(serv_addr));serv_addr.sin_family = AF_INET;if(0 == inet_pton(AF_INET, argv[1], &serv_addr.sin_addr.s_addr)) {printf("\nError: invalid ip\n");return -1;}int port = atoi(argv[2]);if(port < 0) {printf("\nError: invalid port\n");return -1;}serv_addr.sin_port = htons(port);int socketfd = socket(AF_INET, SOCK_STREAM, 0);if(socketfd < 0) {printf("\nError: can not create scoket\n");return -1;}char recvBuffer[1024];bzero(recvBuffer, sizeof(recvBuffer));if(connect(socketfd, (struct sockaddr*)&serv_addr, sizeof(serv_addr)) < 0) {printf("\nError: can not connect to server\n");return -1;}int n = 0;while((n = recv(socketfd, recvBuffer, sizeof(recvBuffer) - 1, 0)) > 0) {recvBuffer[n] = 0;if(fputs(recvBuffer, stdout) == EOF) {printf("\nError: fputs error\n");return -1;}}if(n < 0) {printf("\nRead error\n");return -1;}return 0;
}

运行

编译文件:

g++ server.cpp -o server
g++ client.cpp -o client

运行:
先启动服务器

./server 8001

启动客户端

./client 127.0.0.1 8001

之后客户端的shell显示时间戳数据

参考资料

参考博客:https://www.thegeekstuff.com/2011/12/c-socket-programming/?utm_source=feedburner
参考书籍:Linux高性能服务器编程

Linux下Socket客户端服务器通信相关推荐

  1. linux socket 结构定义 send,Linux下Socket编程中用send发送结构体

    Linux网络通信 Linux下多客户端聊天软件 最近在开发一个Linux下的聊天软件,好久没有做C语言的开发了,感觉到很多东西已经生疏了,这下又碰到用Socket传递结构体的问题,google了一下 ...

  2. 一文了解linux下socket编程

    一文了解linux下socket编程 文章目录 一文了解linux下socket编程 1 网络编程的相关简述 1.1 引言 1.2 Tcp和Udp简介 1.3 TCP三次握手和四次挥手 1.4 网络编 ...

  3. linux下socket和MySQL数据库编程

    一.基本socket函数 Linux系统是通过提供套接字(socket)来进行网络编程的.网络的socket数据传输是一种特殊的I/O,socket也是一种文件描述符.socket也有一个类似于打 开 ...

  4. linux下socket编程读写函数

    linux下socket编程,实现服务器与客户端的通信之后,在同一个虚拟机上,打开两个shell,一个运行服务器程序,一个运行客户端程序,课相互发送数据. 如果使用的是recv接收函数,当关闭客户端或 ...

  5. Linux下Socket编程中用send发送结构体

    转自:http://tech.ddvip.com/2008-10/122543769687623.html Linux网络通信 Linux下多客户端聊天软件 Linux程序设计 Linux socke ...

  6. Linux下Socket编程

    Linux下Socket编程    网络的Socket数据传输是一种特殊的I/O,Socket也是一种文件描述符.Socket也具有一个类似于打开文件的函数调用Socket(),该函数返回一个整型的S ...

  7. Linux下socket编程之UDP简单实现

    本文实现一个简单的UDP小例子,来说明Linux下socket编程之UDP的简单实现.本文主要包括三个部分:服务器端的实现,客服端的实现和通信测试.实现的功能:客服端发送一条消息给服务器端,服务器端把 ...

  8. Linux下Socket编程之TCP应用

    现在,我们用前面所构建的socket类,重新设计<Linux下Socket编程之TCP Server端>中echo的服务器,然后设计客户端程序. echo服务器的工作原理很简单: 1.接收 ...

  9. LINUX下Socket编程 函数格式详解

    你需要了解的一些系统调用: socket() bind() connect() listen() accept() send() recv() sendto() recvfrom() close() ...

最新文章

  1. Python—自动化部署工具:Fabric
  2. 从美图、4399生根,到趣店、瑞幸落户,厦门离中国的西雅图还有多远?
  3. Qt修炼手册5_文件输入输出
  4. 计算机基础知识学前自测,2011计算机二级C语言学前自测题:DOS的基本操作
  5. 番茄花园win11 32位专业版镜像系统v2021.07
  6. 在CSDN写文章头部生成标题目录
  7. lumen 下使用自定义配置文件
  8. 你确定了项目,就不要乱变了
  9. Burpsuite工具的代理抓包功能实验
  10. Java——Set 集合
  11. 【转】spring MVC入门示例(hello world demo)
  12. 安卓原生开机动画_安卓开机动画 74款
  13. 神经网络——激活函数的作用
  14. 程序员在帖子发的问题,底下评论彻底演变成娱乐帖了……
  15. VS2008SP1的MFC测试-(OFFICE2007风格)Ribbon风格(DJ尐舞图形画板2008)
  16. 做ctf题目的时候运行程序就会显示ImportError: cannot import name ‘flag‘ from ‘secret‘ 求大佬解答
  17. 电脑重装了系统开不了机怎么办?
  18. MCDF实验——Lab5
  19. Android含资源文件引用的项目打包成jar包
  20. 九、propTypes验证

热门文章

  1. A Point-Line Feature based Visual SLAM Method in Dynamic Indoor Scene
  2. 你的脑容量(每日一练)
  3. Xilinx FPGA开发板
  4. CUDA——Ubuntu系统上CUDA和cuDNN的安装教程
  5. Python接通图灵机器人
  6. 【搬运】卡尔曼滤波详解及实例
  7. HTML+CSS 轮播图 电商网站注册界面 抽屉主页头部界面
  8. LOJ #6051. 「雅礼集训 2017 Day11」PATH
  9. Beta阶段第2周/共2周 Scrum立会报告+燃尽图 10
  10. 深入浅出UML类图(二)