【linux高级程序设计】(第十五章)UDP网络编程应用 1

UDP网络通信流程

UDP没有connect的过程,故发送数据时需要指明目的地址,不能使用read/write/send/recv. 采用sendto()和recvfrom()

ssize_t sendto (int __fd, __const void *__buf, size_t __n, int __flags, __CONST_SOCKADDR_ADR __addr, socklen_t __addr_len)

向某一主机发送字节序列

参数1:从本机哪个socket发送数据

参数2:欲发送的数据起始地址

参数3:欲发送的数据大小

参数4:说明数据处理方式

参数5:目的主机地址的起始位置

参数6:目的主机地址在内存中的大小

ssize_t recvfrom (int __fd, void *__restrict __buf, size_t __n, int __flags, __SOCKADDR_ARG __addr, socklen_t *__restrict __addr_len)

接收数据

参数5:存储数据的源地址

两个函数的返回值:成功,返回发送或接收的数据的大小;失败返回-1.

例子:UDP通信 发送端发送一句话,接收端接收。

奇怪,这里的发送端又没有bind.

发送端

#include<stdio.h>
#include<stdlib.h>
#include<errno.h>
#include<string.h>
#include<sys/types.h>
#include<netinet/in.h>
#include<netinet/tcp.h>
#include<sys/socket.h>
#include<sys/wait.h>
#include<unistd.h>
#include<arpa/inet.h>
#include<sys/time.h>

int main(int argc, char **argv)
{
    struct sockaddr_in s_addr;
    int sock;
    int addr_len;
    int len;
    char buff[128];
    //创建socket IPv4 UDP 阻塞
    if((sock = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
    {
        perror("socket");
        exit(errno);
    }
    else 
    {
        printf("create socket.

");
    }
    s_addr.sin_family = AF_INET;
    s_addr.sin_port = htons(7838);
    if(argv[1])
    {
        s_addr.sin_addr.s_addr = inet_addr(argv[1]);
    }
    else
    {
        printf("input server ip!
");
        exit(0);
    }
    addr_len = sizeof(s_addr);
    strcpy(buff, "hello i'm here");
    len = sendto(sock, buff, strlen(buff), 0, (struct sockaddr *)&s_addr, addr_len);
    if(len < 0)
    {
        printf("

send error.

");
        return 3;
    }
    printf("send success.

");
    return 0;
}

接收端

#include<stdio.h>
#include<stdlib.h>
#include<errno.h>
#include<string.h>
#include<sys/types.h>
#include<netinet/in.h>
#include<netinet/tcp.h>
#include<sys/socket.h>
#include<sys/wait.h>
#include<unistd.h>
#include<arpa/inet.h>
#include<sys/time.h>

int main(int argc, char **argv)
{
    struct sockaddr_in s_addr;
    struct sockaddr_in c_addr;
    int sock;
    socklen_t addr_len;
    int len;
    char buff[128];
    //创建socket IPv4 UDP
    if((sock = socket(AF_INET, SOCK_DGRAM, 0)) == -1)
    {
        perror("socket");
        exit(errno);
    }
    else
    {
        printf("create socket.

");
    }
    memset(&s_addr, 0, sizeof(struct sockaddr_in));
    s_addr.sin_family = AF_INET;
    s_addr.sin_port = htons(7838);
    s_addr.sin_addr.s_addr = INADDR_ANY;
    //绑定自己的IP信息
    if((bind(sock, (struct sockaddr *)&s_addr, sizeof(s_addr))) == -1)
    {
        perror("bind");
        exit(errno);
    }
    else
    {
        printf("bind address to socket.

");
    }
    addr_len = sizeof(c_addr);
    //一直接收消息
    while(1)
    {
        //接收消息
        len = recvfrom(sock, buff, sizeof(buff) - 1, 0, (struct sockaddr *)&c_addr, &addr_len);
        if(len < 0)
        {
            perror("recvfrom");
            exit(errno);
        }
        buff[len] = '';
        printf("recive come from %s:%d message:%s

", inet_ntoa(c_addr.sin_addr), ntohs(c_addr.sin_port), buff);
    }
    return 0;
}

接收端效果

发送端

原文地址:https://www.cnblogs.com/dplearning/p/4704707.html