Find the answer to your Linux question:
Results 1 to 3 of 3
Hi folks, I tried to construct an IP packet and send that using the RAW Socket, but when I tried to capture the same using packet sniffer (ethereal), it showed ...
Enjoy an ad free experience by logging in. Not a member yet? Register.
  1. #1
    Just Joined!
    Join Date
    Oct 2007
    Posts
    6

    Thumbs up Problem while constructing IP packet and sending using socket() system call


    Hi folks,

    I tried to construct an IP packet and send that using the RAW Socket, but when I tried to capture the same using packet sniffer (ethereal), it showed malformed packet.

    The RAW socket code is as follows:

    int sockraw = socket(AF_INET, SOCK_RAW, htons(ETH_P_IP));

    setsockopt(sd, SOL_SOCKET, SO_BROADCAST,(char *)&one, sizeof(one);

    setsockopt(sd, IPPROTO_IP, IP_HDRINCL,(char *)&one, sizeof(one);

    Can anyone plz let me know what exactly I need to do if I want to construct my own packet (IP/UDP/TCP) etc and send that using RAW Socket. I want to using my own values of various header fields such as TOS, TTL, Source IP Address, Destination IP Address, Source Port and Destination POrt (for UDP/TCP).

    Please guide me how to construct my own IP/UDP/TCP Packet with headers and options.

    Thanks,
    Cavestine

    Code:
    /*Writing some small packet generator
     */
    
    #include <stdio.h>
    #include <sys/time.h>
    #include <netdb.h>
    #include <sys/types.h>
    #include <sys/socket.h>
    #include <unistd.h>
    #include <fcntl.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    #include <netinet/ether.h>
    #include <sys/times.h>
    #include <sys/param.h>
    #include <sys/signal.h>
    #include <netinet/ip.h>
    #include <errno.h>
    #include <netinet/udp.h>
    #include <netinet/ip_icmp.h>
    #include <features.h>    /* for the glibc version number */
    #if __GLIBC__ >= 2 && __GLIBC_MINOR >= 1
    #include <netpacket/packet.h>
    #include <net/ethernet.h>     /* the L2 protocols */
    #else
    #include <asm/types.h>
    #include <linux/if_packet.h>
    #include <linux/if_ether.h>   /* The L2 protocols */
    #endif
    
    #define DEBUG_MESG(arg...) \
                    printf(arg)
    
    struct pseudohdr
    {
            u_int32_t saddr;
            u_int32_t daddr;
            u_int8_t zero;
            u_int8_t proto;
            u_int16_t len;
    };
    
    #define PSEUDOHDR_SIZE sizeof(struct pseudohdr)
    struct sockaddr_in remote;
    struct sockaddr_in local;
    
    u_int16_t cksum(u_int16_t *buf, int nbytes)
    {
            int opt_badcksum = 0;
            u_int32_t sum;
            u_int16_t oddbyte;
    
            sum = 0;
            while (nbytes > 1) {
                    sum += *buf++;
                    nbytes -= 2;
            }
    
            if (nbytes == 1) {
                    oddbyte = 0;
                    *((u_int16_t *) &oddbyte) = *(u_int8_t *) buf;
                    sum += oddbyte;
            }
    
            sum = (sum >> 16) + (sum & 0xffff);
            sum += (sum >> 16);
    
            /* return a bad checksum with --badcksum option */
            if (opt_badcksum) sum ^= 0x5555;
    
            return (u_int16_t) ~sum;
    }
    
    char *udppacket()
    {
            local.sin_addr.s_addr = inet_addr("10.100.12.21");
            remote.sin_addr.s_addr = inet_addr("10.100.12.102");
            char *udppacket;
            struct pseudohdr *pseudohdr;
            int totalsize = sizeof(struct udphdr) + PSEUDOHDR_SIZE;
            udppacket = (char *)malloc(sizeof(struct udphdr) + PSEUDOHDR_SIZE);
            struct udphdr *udphdr;
    
            pseudohdr = (struct pseudohdr *)udppacket;
            udphdr = (struct udphdr *)(udppacket + PSEUDOHDR_SIZE);
    
            memset(udppacket, '0', totalsize);
            memcpy(&pseudohdr->saddr, &local.sin_addr.s_addr, 4);
            memcpy(&pseudohdr->daddr, &remote.sin_addr.s_addr, 4);
            pseudohdr->proto = 17;
            pseudohdr->len = htons(totalsize - PSEUDOHDR_SIZE);
            memset(&(pseudohdr->zero), '0', sizeof(pseudohdr->zero));
    
            udphdr->source = htons(1000);
            udphdr->dest = htons(1200);
            udphdr->len = sizeof(struct udphdr);
            udphdr->check = cksum((u_int16_t *)udppacket, totalsize);
            return (udppacket + PSEUDOHDR_SIZE);
    }
    
    void socket_broadcast(int sd)
    {
            const int one = 1;
    
            if (setsockopt(sd, SOL_SOCKET, SO_BROADCAST,(char *)&one, sizeof(one)) == -1)
            {
                    printf("[socket_broadcast] can't set SO_BROADCAST option\n");
                    /* non fatal error */
            }
    }
    
    void socket_iphdrincl(int sd)
    {
            const int one = 1;
    
            if (setsockopt(sd, IPPROTO_IP, IP_HDRINCL,(char *)&one, sizeof(one)) == -1)
            {
                    printf("[socket_broadcast] can't set IP_HDRINCL option\n");
                    /* non fatal error */
            }
    }
    
    void SendPacket(char *buffer)
    {
            struct sockaddr_in src_addr;
            struct sockaddr_in dest_addr;
    
           int sockraw = socket(AF_INET, SOCK_RAW, IPPROTO_RAW);
            
            const int one = 1;
    
            socket_broadcast(sockraw);
            /* set SO_IPHDRINCL option */
            socket_iphdrincl(sockraw);
    
            src_addr.sin_family = AF_INET;
            src_addr.sin_addr.s_addr = inet_addr("10.100.12.21");
            src_addr.sin_port = htons(9095);
            memset(&src_addr.sin_zero, '\0', 8);
    
            dest_addr.sin_family = AF_INET;
            dest_addr.sin_addr.s_addr = inet_addr("10.100.12.102");
            dest_addr.sin_port = htons(9095);
            memset(&dest_addr.sin_zero, '\0', 8);
       
           if(bind(sockraw, (struct sockaddr *)&src_addr, sizeof(struct sockaddr)) == -1)
            {
                    perror("bind");
            }
    
            if(sendto(sockraw, buffer, sizeof(buffer), 0, (struct sockaddr *)&dest_addr, sizeof(struct sockaddr)) == -1)
            {
                    perror("sendto");
            }
    
    int main()
    {
            char *packet;
       
            int packetsize = sizeof(struct iphdr) + sizeof(struct udphdr);
            packet = (char *)malloc(packetsize + sizeof(struct udphdr));
            struct iphdr *iphdr;
            memset(packet, 0, packetsize);
            iphdr = (struct iphdr *)packet;
            struct sockaddr_in src_addr, dest_addr;
            src_addr.sin_addr.s_addr = inet_addr("10.100.12.21");
            dest_addr.sin_addr.s_addr = inet_addr("10.100.12.102");
    
            char *src, *dest;
            src = (char *)&src_addr.sin_addr;
            dest = (char *)&dest_addr.sin_addr;
    
            iphdr->version = 4;
            iphdr->tos = 10;
            iphdr->id = htons(100);
            iphdr->frag_off = 0;
            iphdr->ttl = 120;
            iphdr->protocol = 17;
            iphdr->check = 0;
            iphdr->tot_len = htons(packetsize);
            iphdr->ihl = htons((sizeof(struct iphdr) + 3) >> 2);
    
            memcpy(&iphdr->saddr, src, sizeof(iphdr->saddr));
            memcpy(&iphdr->daddr, dest, sizeof(iphdr->daddr));
    
            data = (char *)malloc(sizeof(struct udphdr));
            data = udppacket();
            memcpy((packet + sizeof(struct iphdr)), data, sizeof(struct udphdr));
           
            int i;
    
            for(i = 1; i <= 10; i++)
            {
                    SendPacket(packet);
    
            }
    
            return 0;
    }

  2. #2
    Linux Engineer wje_lf's Avatar
    Join Date
    Sep 2007
    Location
    Mariposa
    Posts
    1,192
    See my answer here.

  3. #3
    oz
    oz is offline
    forum.guy
    Join Date
    May 2004
    Location
    arch linux
    Posts
    18,733
    Please don't post duplicate threads all over the forums because it's against the forums rules to do so:

    http://www.linuxforums.org/forum/lin...ums-rules.html

    Your duplicates have been locked, or deleted.
    oz

  4. $spacer_open
    $spacer_close

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •