C语言 构建和发送 RAW 数据报



您好,我想制作一个类似于"SendIP 一个用于发送任意 IP 数据包的命令行工具"的程序

我有一个程序来发送"IPv4 + UDP"。我尝试通过Wireshark验证我的程序,但没有收到任何消息,我不知道为什么。

我通过命令发送它./Project 192.168.1.15 21 192.168.1.15 8080 5

这是我的代码:(在ipv4.h和udp.h中,我有ip和udp标头)

#include <unistd.h>
#include <stdio.h>
#include <sys/socket.h>
#include <netinet/ip.h>
#include <netinet/udp.h>
#include "ipv4.h"
#include "udp.h"
// Source IP, source port, target IP, target port from the command line arguments
int main(int argc, char *argv[])
{
    if (argc != 6)
    {
        printf("- Invalid parameters!!!n");
        printf(
                "- Usage %s <source hostname/IP> <source port> <target hostname/IP> <target port>n",
                argv[0]);
        exit(-1);
    }
    else {
        int sd;
        char buffer[PCKT_LEN];
        struct ipheader *ip = (struct ipheader *) buffer;
        struct udpheader *udp = (struct udpheader *) (buffer
                + sizeof(struct ipheader));
        // Source and destination addresses: IP and port
        struct sockaddr_in sin, din;
        int one = 1;
        const int *val = &one;
        memset(buffer, 0, PCKT_LEN);
        // Create a raw socket with UDP protocol
        sd = socket(PF_INET, SOCK_RAW, IPPROTO_UDP);
        if (sd < 0)
        {
            perror("socket() error");
            // If something wrong just exit
            exit(-1);
        }
        else
            printf(
                    "socket() - Using SOCK_RAW socket and UDP protocol is OK.n");
        // The address family
        sin.sin_family = AF_INET;
        din.sin_family = AF_INET;
        // Port numbers
        sin.sin_port = htons(atoi(argv[2]));
        din.sin_port = htons(atoi(argv[4]));
        // IP addresses
        sin.sin_addr.s_addr = inet_addr(argv[1]);
        din.sin_addr.s_addr = inet_addr(argv[3]);
        ip->iph_ihl = 5;
        ip->iph_ver = 4;
        ip->iph_tos = 16; // Low delay
        ip->iph_len = sizeof(struct ipheader) + sizeof(struct udpheader);
        ip->iph_ident = htons(54321);
        ip->iph_ttl = 64; // hops
        ip->iph_protocol = 17; // UDP
        ip->iph_sourceip = inet_addr(argv[1]);
        // The destination IP address
        ip->iph_destip = inet_addr(argv[3]);
        // Fabricate the UDP header. Source port number, redundant
        udp->udph_srcport = htons(atoi(argv[2]));
        // Destination port number
        udp->udph_destport = htons(atoi(argv[4]));
        udp->udph_len = htons(sizeof(struct udpheader));
        // Calculate the checksum for integrity
        ip->iph_chksum = csum((unsigned short *) buffer,
                sizeof(struct ipheader) + sizeof(struct udpheader));
        if (setsockopt(sd, IPPROTO_IP, IP_HDRINCL, val, sizeof(one)) < 0)
        {
            perror("setsockopt() error");
            exit(-1);
        }
        else
            printf("setsockopt() is OK.n");
        printf("Trying...n");
        printf("Using raw socket and UDP protocoln");
        printf("Using Source IP: %s port: %u, Target IP: %s port: %u.n",
                argv[1], atoi(argv[2]), argv[3], atoi(argv[4]));
        //printf("Interfejs=%dn", *val);
        int count;
        int number = (atoi(argv[5]));
        printf("Number=%dn", number);
        for (count = 1; count <= number; count++)
        {
            if (sendto(sd, buffer, ip->iph_len, 0, (struct sockaddr *) &sin,
                    sizeof(sin)) < 0)
            {
                perror("sendto() error");
                exit(-1);
            }
            else
            {
                printf("Count #%u - sendto() is OK.n", count);
                sleep(2);
            }
        }
        close(sd);
        return 0;
    }
}
好的,

我修复了它。问题出在 int one = 1 上;指定接口数量。我更改为 0 并且它有效。多么愚蠢的错误:D