Linux:在接口上环回传入的数据包

时间:2013-01-28 08:27:07

标签: linux networking routing ip iptables

将接口上发送的数据包发送回同一接口而不更改数据包中的任何内容的最佳方法是什么。我希望对我的某个接口上的实际流量产生环回效果,例如eth0

2 个答案:

答案 0 :(得分:1)

我认为你不能通过物理接口轻松完成这项工作。不过,我使用了水龙头模块。这很简单:我创建了一个新的tap接口,我的程序会回写从设备读取的所有内容。我用这个来测试一个专有的网络协议 - 所以它可能会或可能不适用于你打算做的事情。代码非常简单:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/ioctl.h>
#include <net/if.h>

#include <linux/if_tun.h>

#define DEVNAME "gnlo0"

static int tun_alloc(char *dev)
{
    struct ifreq ifr;
    int fd, ret;

    if ((fd = open("/dev/net/tun", O_RDWR)) < 0) {
        perror("open");
        return -1;
    }

    memset(&ifr, 0, sizeof(ifr));

    ifr.ifr_flags = IFF_TAP;
    if (*dev)
        strncpy(ifr.ifr_name, dev, IFNAMSIZ);

    ret = ioctl(fd, TUNSETIFF, (void *)&ifr);
    if (ret < 0) {
        close(fd);
        perror("ioctl TUNSETIFF");
        return ret;
    }
    strcpy(dev, ifr.ifr_name);
    return fd;
}

int main(int argc, char **argv)
{
    int fd = -1;
    int ret = 1;
    char dev[IFNAMSIZ];
    strncpy(dev, DEVNAME, IFNAMSIZ - 1);
    printf("opening %s\n", dev);

    fd = tun_alloc(dev);
    if (fd < 0)
        goto out;

    char buf[512];
    snprintf(buf, sizeof(buf) - 1,
             "ip addr flush dev %s; ip link set dev %s up", dev, dev);
    if (system(buf) < 0) {
        perror("system");
        goto out;
    }

    while (1) {
        unsigned char packet[65535];
        int len = read(fd, packet, sizeof(packet));
        if (len < 0) {
            perror("read");
            goto out;
        }
        printf("incoming packet [%d octets]\n", len);

        len = write(fd, packet, len);
        printf("fed back packet [%d octets]\n", len);
    }
    ret = 0;

out:
    if (fd >= 0)
        close(fd);
    return ret;
}

答案 1 :(得分:1)

我认为你可以通过Python / Scapy轻松实现这一目标。像

这样的东西

sniff(iface="eth0", prn=lambda x: sendp(x, iface="eth0"))

应该这样做。