AF_LINK未在bits / socket.h和sys / socket.h中定义

时间:2015-03-11 20:33:54

标签: c++ c sockets network-programming packet

我正在编写一个代码来从接口读取MAC地址以列出接口及其MAC地址,因为我无法在任何一个socket.h文件中找到AF_LINK定义。

根据互联网资源,我将在下面看到:

#define AF_LINK     18      /* Link layer interface */

但我的bits / socket.h包含:

#define PF_ASH      18  /* Ash.  */
.
.
#define AF_ASH      PF_ASH

我应该使用PF_ASH代替AF_LINK吗?

以下是我使用AF_LINK的代码部分:

    if ((family == AF_LINK) && (ifa->ifa_name[0] == 'e')) {

            //This is for extracting interface number from interface name// 
            char newi[3];
            int i, j;
            for (i=0, j=0; i < strlen(ifa->ifa_name); i++) {
                if (ifa->ifa_name[i] >= '0' && ifa->ifa_name[i] <= '9') {
                    newi[j++] = ifa->ifa_name[i];
                }
             }
             newi[j] = '\0';

            if_num = atoi(newi);

            printf("Interface %d : %d\n", k++, if_num);
    }

完整代码:

/*
 * ethernetsocket.c
 *
 *  Created on: Feb 25, 2015
 *      Author: tsp3859
 */

#include <arpa/inet.h>
#include <linux/if_packet.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <bits/socket.h>
#include <net/if.h>
#include <netinet/ether.h>

#include <ifaddrs.h>


#define MY_DEST_MAC0    0xff
#define MY_DEST_MAC1    0xff
#define MY_DEST_MAC2    0xff
#define MY_DEST_MAC3    0xff
#define MY_DEST_MAC4    0xff
#define MY_DEST_MAC5    0xff

// Source Ethernet interface
#define DEFAULT_InterFace   "eth0"
#define DEFAULT_PayLoad     "1.1.10"

// Allocating size to different containers
#define MAX_FRAME_SIZE      1024
#define MAX_PAYLD_SIZE      1000
#define HEADER_SIZE         14

int payLoad_Size = -1;
int frame_Size = -1;

int main(int argc, char *argv[]) {
    int sockfd;
    struct ifreq if_idx; // destination ethernet (optional)
    struct ifreq if_mac; // destination mac address

    int tx_len = 0;      // header counter
    char ifName[IFNAMSIZ]; // interface name

    uint8_t header[HEADER_SIZE]; // ethernet header
    char dummy_Payload[MAX_PAYLD_SIZE];

    int if_num; // interface number, used for genarating VID

    /*
     * Run as one of the following command
     * 1.   ./a.out
     * 2    ./a.out eth3
     * 3.   ./a.out eth4 PayLoad
     */

    // Get Ethernet interface name from command line (optional)
    if (argc > 1) {

        if (argc == 2) {

            strcpy(ifName, argv[1]);
            strcpy(dummy_Payload, DEFAULT_PayLoad);
        }

        if (argc == 3) {

            strcpy(ifName, argv[1]);

            if (strlen(argv[2]) > 1000) {

                memcpy(dummy_Payload, argv[2], MAX_PAYLD_SIZE);
            } else
                strcpy(dummy_Payload, argv[2]);
        }
    } else {

        // Default case: All fields are optional
        if (argc < 2) {
            strcpy(ifName, DEFAULT_InterFace);
            strcpy(dummy_Payload, DEFAULT_PayLoad);
        }
    }

    //Getting interface number
    struct ifaddrs *ifaddr, *ifa;
    int family, s, n;
           if (getifaddrs(&ifaddr) == -1) {
               perror("getifaddrs");
               exit(EXIT_FAILURE);
           }
    int k = 1; // Interface SNo.
    for (ifa = ifaddr, n = 0; ifa != NULL; ifa = ifa->ifa_next, n++) {
               if (ifa->ifa_addr == NULL)
                   continue;

               family = ifa->ifa_addr->sa_family;


        if ((family == AF_INET || family == AF_INET6) && (ifa->ifa_name[0] == 'e')) {

                char newi[3];

                int i, j;
                 for (i=0, j=0; i < strlen(ifa->ifa_name); i++) {
                    if (ifa->ifa_name[i] >= '0' && ifa->ifa_name[i] <= '9') {
                        newi[j++] = ifa->ifa_name[i];

                        }
                 }
                 newi[j] = '\0';

                if_num = atoi(newi);
                 printf("Interface %d : %d\n", k++, if_num);
        }
    }


    // Setting frame size
    payLoad_Size = strlen(dummy_Payload);


    // Setting payload, contains VID
    char payLoad[payLoad_Size];
    //memcpy(payLoad,dummy_Payload,payLoad_Size);

    int len=0;
    payLoad[len++]=1;
    payLoad[len++]=1;
    payLoad[len]=10;

    frame_Size = HEADER_SIZE + strlen(payLoad);
    //printf("Payload size is %d\n ", payLoad_Size);
    printf("Frame size is %d\n ", frame_Size);

    printf("Payload size is %d\n\n ", strlen(payLoad));
    payLoad_Size=strlen(payLoad);
    // creating frame
    uint8_t frame[frame_Size];

    struct ether_header *eh = (struct ether_header *) header;
    struct sockaddr_ll socket_address;

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

    memset(&if_idx, 0, sizeof(struct ifreq));
    strncpy(if_idx.ifr_name, ifName, IFNAMSIZ - 1);
    if (ioctl(sockfd, SIOCGIFINDEX, &if_idx) < 0)
        perror("SIOCGIFINDEX - Misprint Compatibility");

    memset(&if_mac, 0, sizeof(struct ifreq));
    strncpy(if_mac.ifr_name, ifName, IFNAMSIZ - 1);
    if (ioctl(sockfd, SIOCGIFHWADDR, &if_mac) < 0)
        perror(
                "SIOCGIFHWADDR - Either interface is not correct or disconnected");

    // Initializing the Ethernet Header
    memset(header, 0, HEADER_SIZE);

    // Print-test initial header
    printf("Zeros: %02x:%02x:%02x:%02x:%02x:%02x   %02x:%02x:%02x:%02x:%02x:%02x    %02x:%02x\n",
            header[0], header[1], header[2], header[3], header[4], header[5],
            header[6], header[7], header[8], header[9], header[10], header[11],
            header[12], header[13]);

    /*
     *  Ethernet Header - 14 bytes
     *
     *  6 bytes - Source MAC Address
     *  6 bytes - Destination MAC Address
     *  2 bytes - EtherType
     *
     */

    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] = MY_DEST_MAC0;
    eh->ether_dhost[1] = MY_DEST_MAC1;
    eh->ether_dhost[2] = MY_DEST_MAC2;
    eh->ether_dhost[3] = MY_DEST_MAC3;
    eh->ether_dhost[4] = MY_DEST_MAC4;
    eh->ether_dhost[5] = MY_DEST_MAC5;

    eh->ether_type = htons(0x8010);

    tx_len += sizeof(struct ether_header);

    // Copying header to frame
    memcpy(frame, header, 14);

    // Copying payLoad to frame
    //printf("Payload: %d\n", payLoad[1]);
    memcpy(frame + 14, payLoad, strlen(payLoad));

    // Printing initial frame
    printf(" Frame: %02x:%02x:%02x:%02x:%02x:%02x   %02x:%02x:%02x:%02x:%02x:%02x    %02x:%02x\n",
            frame[0], frame[1], frame[2], frame[3], frame[4], frame[5],
            frame[6], frame[7], frame[8], frame[9], frame[10], frame[11],
            frame[12], frame[13]);

    // Printing payLoad
    printf("Payload: %d.%d.%d\n", frame[14],frame[15],frame[16]);

    // Index of the network device
    socket_address.sll_ifindex = if_idx.ifr_ifindex;

    // Address length - 6 bytes
    socket_address.sll_halen = ETH_ALEN;

    // Destination MAC Address
    socket_address.sll_addr[0] = MY_DEST_MAC0;
    socket_address.sll_addr[1] = MY_DEST_MAC1;
    socket_address.sll_addr[2] = MY_DEST_MAC2;
    socket_address.sll_addr[3] = MY_DEST_MAC3;
    socket_address.sll_addr[4] = MY_DEST_MAC4;
    socket_address.sll_addr[5] = MY_DEST_MAC5;

    // Send packet
    if (sendto(sockfd, frame, tx_len + strlen(payLoad), 0,
            (struct sockaddr*) &socket_address, sizeof(struct sockaddr_ll)) < 0)
        printf("Send failed\n");

freeifaddrs(ifaddr);
exit(EXIT_SUCCESS);
    return 0;
}

0 个答案:

没有答案