Search code examples
cwifibroadcastraw-sockets

Socket program for sending broadcast a packet over wifi radio to a device in its range


I want to run a program for sending my own packet to the environment over wifi radio. As my knowledge, this work can be done if I send a ethernet frame to the dest Mac address ff:ff:ff:ff:ff:ff. So i opened a raw socket and constructed the ethernet header following code.

/* Open RAW socket to send on */
    if ((sockfd = socket(AF_PACKET, SOCK_RAW, IPPROTO_RAW)) == -1) {
        perror("socket");
    }

    /* Get the index of the interface to send on */
    memset(&if_idx, 0, sizeof(struct ifreq));
    strncpy(if_idx.ifr_name, ifName, IFNAMSIZ-1);
    if (ioctl(sockfd, SIOCGIFINDEX, &if_idx) < 0)
        perror("SIOCGIFINDEX");
    /* Get the MAC address of the interface to send on */
    memset(&if_mac, 0, sizeof(struct ifreq));
    strncpy(if_mac.ifr_name, ifName, IFNAMSIZ-1);
    if (ioctl(sockfd, SIOCGIFHWADDR, &if_mac) < 0)
        perror("SIOCGIFHWADDR");

    /* Construct the Ethernet header */
    memset(sendbuf, 0, BUF_SIZ);
    /* Ethernet header */
    eh->ether_shost[0] = ((uint8_t *)&if_mac.ifr_hwaddr.sa_data)[0];
    eh->ether_shost[1] = ((uint8_t *)&if_mac.ifr_hwaddr.sa_data)[1];
    eh->ether_shost[2] = ((uint8_t *)&if_mac.ifr_hwaddr.sa_data)[2];
    eh->ether_shost[3] = ((uint8_t *)&if_mac.ifr_hwaddr.sa_data)[3];
    eh->ether_shost[4] = ((uint8_t *)&if_mac.ifr_hwaddr.sa_data)[4];
    eh->ether_shost[5] = ((uint8_t *)&if_mac.ifr_hwaddr.sa_data)[5];
    eh->ether_dhost[0] = 0xff;
    eh->ether_dhost[1] = 0xff;
    eh->ether_dhost[2] = 0xff;
    eh->ether_dhost[3] = 0xff;
    eh->ether_dhost[4] = 0xff;
    eh->ether_dhost[5] = 0xff;
    /* Ethertype field */
    eh->ether_type = htons(ETH_P_BATMAN);
    tx_len += sizeof(struct ether_header);

    /* Packet data */
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;
    sendbuf[tx_len++] = 0xaa;

I tested this program on an router run in AP mode, but the problem is I could only receive this packet when i access in it WLAN SSID. My question is how i can receive this packet when i am in this router transmission range without connect to it ssid. Any help would be appreciated.


Solution

  • As my knowledge, this work can be done if I send a ethernet frame to the dest Mac address ff:ff:ff:ff:ff:ff.

    Nope, that's not how this works.

    Joining an SSID is analogous to plugging in an Ethernet adapter to a physical Ethernet network. If you're not plugged into a network on a regular wired Ethernet adapter, you can't send packets to devices on that network. With WiFi adapters, until you join the SSID, you can't communicate with other devices on that network.

    The lower layers of WiFi are typically inaccessible to your application. There are some WiFi adapters available for debugging that allow you to listen and transmit arbitrary 802.11a/b/g/n frames, for things like beacons, probes, and others. None of these management frames are intended to carry traffic.

    If you want to send data between a couple devices that haven't been set up to communicate with each other, you should have them join an ad-hoc SSID. Then, broadcast traffic on the network as usual.