socket本地通信


int socket_srv_ipc_init(void)
{
    int ret = 0;
    char path[64] = {0};

    //基于本地的TCP通信
    int fd = socket(AF_LOCAL, SOCK_STREAM, 0);
    if (fd < 0)
    {
        log_e("socket error [%s]", strerror(errno));
        return -1;
    }

    snprintf(path, sizeof(path), "%s/%s", IPC_BASE_PATH, SOCKET_IPC_FILE);

    //如果文件存在则删除
    if(access(path, F_OK) == 0)
        unlink(path);

    //填充数据
    struct sockaddr_un srv;
    bzero(&srv, sizeof(srv));
    srv.sun_family = AF_LOCAL;
    strcpy(srv.sun_path, path);

    //绑定
    ret = bind(fd, (struct sockaddr *)&srv, sizeof(srv));
    if(ret < 0)
    {
        log_e("bind error [%s]", strerror(errno));
        goto error;
    }

    //监听客户断
    ret = listen(fd, 5);
    if (ret < 0)
    {
        log_e("listen error [%s]", strerror(errno));
        goto error;
    }

    return fd;
error:
    close(fd);
    return -1;
}
 

int socket_client_ipc_init(void)
{
    int ret = 0;
    char path[64] = {0};

    //基于本地的TCP通信
    int fd = socket(AF_LOCAL, SOCK_STREAM, 0);
    if (fd < 0)
    {
        log_e("socket error [%s]\n", strerror(errno));
        return -1;
    }

    snprintf(path, sizeof(path), "%s/%s", IPC_BASE_PATH, SOCKET_IPC_FILE);

    //确保IPC文件存在且可写
    if(access(path, F_OK|W_OK) < 0)
    {
        log_e("error: [%s] not exist\n", path);
        exit(-1);
    }

    //填充struct sockaddr_un*/
    struct sockaddr_un srv;
    bzero(&srv, sizeof(srv));

    srv.sun_family = AF_LOCAL;
    strcpy(srv.sun_path, path);

    //连接服务端
    ret = connect(fd, (struct sockaddr *)&srv, sizeof(srv));
    if(ret < 0)
    {
        log_e("connect error [%s]\n", strerror(errno));
        goto error;
    }

    return fd;
error:
    close(fd);
    return -1;
}

void *cfg_server_task(void *data)
{
    assert(data);
    int ret = 0;
    struct manager_data *pdata = (struct manager_data *)data;

    int srvfd = socket_srv_ipc_init();
    if (srvfd < 0)
    {
        log_e("socket ipc init error");
        exit(-1);
    }

    log_w("wait for client connnect...");

    fd_set fds, tmpfds;
    int maxfd = 0;

    FD_ZERO(&fds);
    FD_SET(srvfd, &fds);
    maxfd = MAX(maxfd, srvfd);
    log_i("add server socket [%d]", srvfd);

    while (1)
    {
        tmpfds = fds;

        ret = select(maxfd + 1, &tmpfds, NULL, NULL, NULL);
        if (ret <= 0)
        {
            log_e("select error [%s]", strerror(errno));
            continue;
        }

        for (int fd=0; fd<=maxfd; fd++)
        {
            if(FD_ISSET(fd, &tmpfds))
            {
                if (fd == srvfd)
                {
                    int clifd = accept(srvfd, NULL, NULL);
                    if (clifd > 0)
                    {
                        FD_SET(clifd, &fds);
                        maxfd = MAX(maxfd, clifd);
                        log_i("add client socket [%d]", clifd);
                    }
                }
                else
                {
                    char recvbuf[128] = {0};
                    ret = recv(fd, recvbuf, sizeof(recvbuf), 0);
                    if (ret > 0)
                    {
                        log_i("recv: %s", recvbuf);
                    }
                    else
                    {
                        if (errno == EINTR || errno == EWOULDBLOCK || errno == EAGAIN)
                            continue;

                        close(fd);
                        FD_CLR(fd, &fds);
                        log_w("client off-line socket [%d]", fd);
                    }
                }
            }
        }
    }

    close(srvfd);
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值