C 中的 UDP 套接字

发布于 2024-08-12 22:43:14 字数 1263 浏览 2 评论 0原文

我正在解决课堂作业问题。我想启动一个 UDP 服务器来侦听文件请求。它打开文件并使用 UDP 将其发送回请求客户端。

这是服务器代码。

    // Create UDP Socket
    if ((sockfd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) {
        perror("Can't create socket");
        exit(-1);
    }

    // Configure socket
    memset(&server, 0, sizeof server);
    server.sin_family = AF_INET; // Use IPv4
    server.sin_addr.s_addr = htonl(INADDR_ANY); // My IP
    server.sin_port = htons(atoi(argv[1])); // Server Port

    // Bind socket
    if ((bind(sockfd, (struct sockaddr *) &server, sizeof(server))) == -1) {
        close(sockfd);
        perror("Can't bind");
    }

    printf("listener: waiting to recvfrom...\n");
    if (listen(sockfd, 5) == -1) {
        perror("Can't listen for connections");
        exit(-1);
    }

while (1) {
    client_len = sizeof(struct sockaddr_in);
    newsockfd = accept(sockfd, (struct sockaddr*)&client,&client_len);

    if (newsockfd < 0) {
        perror("ERROR on accept");
    }

    // Some how parse request
    // I do I use recv or recvfrom?
    // I do I make new UDP socket to send data back to client?

    sendFile(newsockfd, filename);

    close(newsockfd);
}

close(sockfd);

我有点迷失了如何从客户端接收数据?如何建立一个新的 UDP 连接返回客户端?

I'm working on a homework problem for class. I want to start a UDP Server that listens for a file request. It opens the file and sends it back to the requesting client with UDP.

Heres the server code.

    // Create UDP Socket
    if ((sockfd = socket(AF_INET, SOCK_DGRAM, 0)) == -1) {
        perror("Can't create socket");
        exit(-1);
    }

    // Configure socket
    memset(&server, 0, sizeof server);
    server.sin_family = AF_INET; // Use IPv4
    server.sin_addr.s_addr = htonl(INADDR_ANY); // My IP
    server.sin_port = htons(atoi(argv[1])); // Server Port

    // Bind socket
    if ((bind(sockfd, (struct sockaddr *) &server, sizeof(server))) == -1) {
        close(sockfd);
        perror("Can't bind");
    }

    printf("listener: waiting to recvfrom...\n");
    if (listen(sockfd, 5) == -1) {
        perror("Can't listen for connections");
        exit(-1);
    }

while (1) {
    client_len = sizeof(struct sockaddr_in);
    newsockfd = accept(sockfd, (struct sockaddr*)&client,&client_len);

    if (newsockfd < 0) {
        perror("ERROR on accept");
    }

    // Some how parse request
    // I do I use recv or recvfrom?
    // I do I make new UDP socket to send data back to client?

    sendFile(newsockfd, filename);

    close(newsockfd);
}

close(sockfd);

I'm kind of lost how do I recv data from the client? And how to I make a new UDP connection back to the client?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

别念他 2024-08-19 22:43:14

UDP 与 TCP 有何不同:

  • 面向消息,而不是面向流。您不读/写或发送/接收。您发送至/接收自。消息大小限制为 64K。每次调用 recvfrom 都会收到一条由调用 sendto 发送的消息。如果recvfrom传递的缓冲区小于消息的大小,则消息的其余部分将永远消失。

  • 没有连接。因此没有监听/接受/连接。您向特定地址/端口发送消息。当您接收消息(在套接字绑定的地址/端口上)时,您将收到传入消息的源作为recvfrom 的输出参数。

  • 没有任何保证。消息可能会被丢弃或乱序接收。如果我没记错的话,它们不能被截断。

最后一句警告 - 您可能会发现自己在 UDP 上重新发明了 TCP。在这种情况下,请停止并返回到 TCP。

How UDP is different from TCP:

  • message-oriented, not stream-oriented. You don't read/write or send/recv. You sendto/recvfrom. The size of message is limited to 64K. Each call to recvfrom gets one message sent by a call to sendto. If recvfrom passes a buffer that's smaller than the size of message, the rest of message is gone for good.

  • no connections. Therefore no listen/accept/connect. You send a message to a particular address/port. When you receive message (on the address/port to which your socket is bound), you get the source of the incoming message as an output parameter to recvfrom.

  • no guarantees. The messages can be dropped or received out of order. If I remember correctly, they cannot be truncated, though.

One last word of caution - you may find yourself re-inventing TCP over UDP. In that case, stop and go back to TCP.

浅浅 2024-08-19 22:43:14

我用 C 编写了一个UDP 服务器客户端,其中客户端发送注册号,服务器给出一个名称作为反馈。

服务器

0. Variable initialization
1. sock()
2. bind()
3. recvfrom()
4. sendto()

客户端

0. gethostbyname()
1. sock()
2. bzero()
4. sendto()
5. recvfrom()

希望有帮助。您可以在此处找到示例代码 udp 服务器/客户端< /a>

I have written a UDP server-client in C , where the client sends a registration number and the server gives a name as the feedback.

SERVER

0. Variable initialization
1. sock()
2. bind()
3. recvfrom()
4. sendto()

CLIENT

0. gethostbyname()
1. sock()
2. bzero()
4. sendto()
5. recvfrom()

Hope it helps. You can find the example code here udp server/client

拥抱没勇气 2024-08-19 22:43:14

Accept 仅用于面向连接(STREAM)的套接字。 UDP不是面向流的,因此没有连接,您不能使用accept(2)——它将返回EOPNOTSUPP。

相反,您只需直接从绑定的服务套接字读取数据包(通常使用recvfrom(2),这样您就可以知道数据包来自哪里,尽管您可以使用recv,或者如果您不关心也可以只读取),之后您可以将数据包发回使用相同的套接字(通常使用 sendto(2))

accept is only used for connection oriented (STREAM) sockets. UDP is not stream, oriented, so there are no connections and you can't use accept(2) -- it will return EOPNOTSUPP.

Instead, you just read packets directly from the bound service socket (generally using recvfrom(2) so you can tell where thy came from, though you can use recv or just read if you don't care), afterwhich you can send packets back using the same socket (and generally using sendto(2))

送舟行 2024-08-19 22:43:14

请记住,UDP 是无连接的。它仅发送数据包,不适合发送文件 - 除非整个内容适合一个 UDP 数据包。

如果您无论如何想发送/接收 UDP 数据包,您只需调用 sendto/recvfrom 并使用适当的地址。

Keep in mind that UDP is connectionless. It only sends packets, and is not suitable for sending files - unless the entire content fit in one UDP packet.

If you anyway want to send/receive UDP packets, you simply call sendto/recvfrom with the appropriate addresses.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文