91超碰碰碰碰久久久久久综合_超碰av人澡人澡人澡人澡人掠_国产黄大片在线观看画质优化_txt小说免费全本

溫馨提示×

?Linux非阻塞connect錯誤碼EINPROGRESS怎么解決

小億
545
2023-11-15 13:42:38
欄目: 編程語言

當使用非阻塞(connect)時,可能會返回錯誤碼EINPROGRESS,表示連接正在進行中。這是因為非阻塞連接是異步的,它會立即返回并在后臺進行連接操作。為了解決這個問題,你可以使用以下方法之一:

  1. 使用select或epoll等多路復用技術,等待連接完成。這樣你可以在連接完成后再繼續進行后續操作。

  2. 使用非阻塞IO時,可以使用poll或epoll等函數來檢查連接是否已經建立。你可以通過檢查套接字的可寫事件來判斷連接是否已經建立。

  3. 使用非阻塞IO時,可以使用非阻塞的connect函數,它會立即返回,但是需要不斷地使用poll或epoll等函數來檢查連接狀態,直到連接完成。

下面是一個使用非阻塞connect的示例代碼:

#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <errno.h>

int connect_nonblock(int sockfd, const struct sockaddr *addr, socklen_t addrlen, int timeout) {
    int flags, ret;
    fd_set rset, wset;
    struct timeval tv;

    // 設置套接字為非阻塞模式
    flags = fcntl(sockfd, F_GETFL, 0);
    fcntl(sockfd, F_SETFL, flags | O_NONBLOCK);

    // 發起非阻塞連接
    ret = connect(sockfd, addr, addrlen);
    if (ret == 0) {
        // 連接成功,恢復套接字阻塞模式
        fcntl(sockfd, F_SETFL, flags);
        return ret;
    } else if (ret < 0 && errno != EINPROGRESS) {
        // 連接出錯
        return ret;
    }

    // 使用select等待連接完成
    FD_ZERO(&rset);
    FD_SET(sockfd, &rset);
    wset = rset;
    tv.tv_sec = timeout;
    tv.tv_usec = 0;

    ret = select(sockfd + 1, &rset, &wset, NULL, &tv);
    if (ret <= 0) {
        // 連接超時或出錯
        return ret;
    }

    if (FD_ISSET(sockfd, &rset) || FD_ISSET(sockfd, &wset)) {
        // 連接完成,恢復套接字阻塞模式
        fcntl(sockfd, F_SETFL, flags);
        return ret;
    }

    // 連接超時
    errno = ETIMEDOUT;
    return -1;
}

int main() {
    int sockfd;
    struct sockaddr_in servaddr;

    sockfd = socket(AF_INET, SOCK_STREAM, 0);

    bzero(&servaddr, sizeof(servaddr));
    servaddr.sin_family = AF_INET;
    servaddr.sin_port = htons(80);
    inet_pton(AF_INET, "127.0.0.1", &servaddr.sin_addr);

    if (connect_nonblock(sockfd, (struct sockaddr *)&servaddr, sizeof(servaddr), 5) < 0) {
        perror("connect_nonblock");
        return -1;
    }

    // 連接完成,進行后續操作
    // ...

    close(sockfd);

    return 0;
}

這個示例代碼使用了select函數來等待連接完成,可以根據自己的需求選擇使用其他多路復用技術來替代select。在connect_nonblock函數中,首先將套接字設置為非阻塞模式,然后發起非阻塞連接。如果連接成功,恢復套接字阻塞模式并返回。如果連接出錯,直接返回錯誤碼。如果連接未完成,則使用select等待連接完成,并在連接完成后恢復套接字阻塞模式并返回。如果連接超時,則返回錯誤碼ETIMEDOUT。

0
收藏| 扎赉特旗| 吉安市| 香格里拉县| 金山区| 社旗县| 蒙山县| 广水市| 九龙城区| 奇台县| 山东| 胶南市| 教育| 沅江市| 五寨县| 巴南区| 海丰县| 防城港市| 文安县| 五指山市| 滦南县| 修武县| 新安县| 海丰县| 乐陵市| 肥西县| 汾阳市| 彰化市| 通山县| 西青区| 景泰县| 大邑县| 砀山县| 兴海县| 广水市| 鞍山市| 大关县| 铜鼓县| 乡城县| 肥西县| 平顶山市|