【Linux系统编程】TCP实现--socket

使用套接字socket实现服务器和客户端之间的TCP通信。

流程如下:

实现代码:

c 复制代码
/* server.c */
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <arpa/inet.h>
#include <sys/types.h>          /* See NOTES */
#include <sys/socket.h>
#include <errno.h>
#include <ctype.h>

#define SERV_PORT 9527

void sys_err(const char *str)
{
    perror(str);
    exit(1);
}


int main(int argc, char *argv[])
{
    struct sockaddr_in serv_addr, client_addr;
    socklen_t client_addr_len;
    char buf[BUFSIZ], client_IP[1024];
    //1. 创建监听套接字
    int lfd = socket(AF_INET,  //IPV4
                    SOCK_STREAM, 
                    0);
    if(lfd == -1) //check RETURN VALUE
    {
        sys_err("socket error");
    }
    //2. 绑定本地的IP地址和端口号
    serv_addr.sin_family = AF_INET;
    serv_addr.sin_port = htons(SERV_PORT);
    serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);

    int ret = bind(lfd,  (struct sockaddr *)&serv_addr, sizeof(serv_addr));
    if(ret == -1)
    {
        sys_err("bind error");
    }

    //3. 设置监听
    int ret_listen = listen(lfd, 128);
    if(ret_listen == -1)
    {
        sys_err("listen error");
    }
    
    //4. 阻塞等待,连接的到达,连接成功后返回通信用的套接字
    client_addr_len = sizeof(client_addr);
    int cfd = accept(lfd, (struct sockaddr*)&client_addr, &client_addr_len);
    if(cfd == -1)
    {
        sys_err("accept error");
    }
    printf("client ip is %s, port is %d\n",
             inet_ntop(AF_INET, &client_addr.sin_addr.s_addr, client_IP, sizeof(client_IP)),
             ntohs(client_addr.sin_port));

    //5. 开始通信
    while(1)
    {
        ssize_t ret_acc = read(cfd, buf, sizeof(buf));
        write(STDOUT_FILENO, buf, ret_acc);

        for(int i = 0; i < ret_acc; i++)
        {
            buf[i] = toupper(buf[i]);
        }
        write(cfd, buf, ret_acc);
    }

    close(lfd);
    close(cfd);

    return 0;
}
c 复制代码
/* client.c */
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <arpa/inet.h>
#include <sys/types.h>          /* See NOTES */
#include <sys/socket.h>
#include <errno.h>
#include <ctype.h>

#define SERV_PORT 9527

void sys_err(const char *str)
{
    perror(str);
    exit(1);
}


int main(int argc, char *argv[])
{
    int cfd;
    struct sockaddr_in serv_addr;
    serv_addr.sin_family = AF_INET;
    serv_addr.sin_port = htons(SERV_PORT);
    inet_pton(AF_INET, "127.0.0.1", &serv_addr.sin_addr.s_addr);
    char buf[BUFSIZ];
    int cnt = 10;

    //1. 创建监听套接字
    cfd = socket(AF_INET, SOCK_STREAM, 0);
    if(cfd == -1) 
    {
        sys_err("socket error");
    }

    int ret = connect(cfd, (struct sockaddr *)&serv_addr, sizeof(serv_addr));
    if(ret != 0)
    {
        sys_err("connect error");
    }

    while(cnt--)
    {
        write(cfd, "hello\n", 6);
        ret = read(cfd, buf, sizeof(buf));
        write(STDERR_FILENO, buf, ret);
        sleep(1);

    }

    close(cfd);

    return 0;
}

实验现象

客户端向服务器发送10次hello,接收到服务器发来的10次大写HELLO;服务器首先打印IP地址和端口号,随后打印收到的10次由客户端传来的hello。

相关推荐
星恒随风8 小时前
MySQL 从零入门(五):MySQL 内置函数详解——日期、字符串、数学函数与实战案例
linux·数据库·笔记·sql·mysql
唐墨12313 小时前
linux kernel 比较数据大小的宏定义
linux·算法
程序开发阿元13 小时前
密码不进工具:一个独立开发者的服务器凭据管理办法
linux·ssh
AR-26710-16 小时前
Linux Day33——定时任务+lvm
linux·运维
墨痕诉清风17 小时前
SSRF漏洞实战记录+OSS桶命令执行+MCP漏洞
linux·服务器·数据库
byte轻骑兵17 小时前
实战 4:BlueZ 源码中添加自定义设备过滤规则
linux·物联网·bluez·电脑蓝牙·嵌入式蓝牙
略懂而已17 小时前
安装SSL后网站速度变慢?
网络·网络协议·ssl
瓦瓦gogo18 小时前
从一个 TypeScript 函数开始理解 MCP 协议
linux·ubuntu·typescript
云上工程笔记19 小时前
RDMA / IB 高速互联 GPU 云对比:多机训练网络性能与价格
网络·gpu算力·gpu
鱼听禅19 小时前
Ubuntu安装YOLOv8进行菌落识别训练
linux·python·yolo·ubuntu