有时候测试虚拟交换机需要打流量,每次创建虚拟机太麻烦,所以写了一个可以直接向端口打流量的小程序,buff是报文内容。
unsigned char str2hex(char x)
{
if (x >= '0' && x <= '9') {
return x - 48;
} else if (x >= 'a' && x <= 'z') {
return x - 97 + 10;
} else if (x >= 'A' && x <= 'Z') {
return x - 65 + 10;
} else {
return 255;
}
}
void mac_convert(char *str, unsigned char *mac)
{
int i;
for (i = 0; i < 6; i++) {
mac[i] = (str2hex(str[i*2]) << 4) + str2hex(str[i*2 +1]);
}
}
static int getifindex(int fd, const char *device)
{
struct ifreq ifr;
int ret;
memset(&ifr, 0, sizeof(ifr));
strncpy(ifr.ifr_name, device, sizeof(ifr.ifr_name));
ret = ioctl(fd, SIOCGIFINDEX, &ifr);
if (ret < 0) {
return -1;
}
return ifr.ifr_ifindex;
}
void usage()
{
printf("usage:\n");
printf("\t./a.out ifname dstmac srcmac\n");
}
int main(int argc, char **argv)
{
unsigned char buff[512] = "\x00.....";
int fd;
int ifindex;
struct sockaddr_ll sa;
unsigned char mac[6];
if (argc < 2) {
usage();
return -1;
}
if (strcmp(argv[1], "-help") == 0) {
usage();
return 0;
}
fd = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_ALL));
ifindex = getifindex(fd, argv[1]);
sa.sll_family = AF_PACKET;
sa.sll_ifindex = ifindex;
sa.sll_protocol = htons(0x0003);
if (bind(fd, (struct sockaddr *)&sa, sizeof(sa)) < 0) {
perror("bind error");
return -1;
}
if (argv[2] != NULL) {
mac_convert(argv[2], mac);
memcpy(&buff[0], mac, 6);
}
if (argv[3] != NULL) {
mac_convert(argv[3], mac);
memcpy(&buff[6], mac, 6);
}
while (1) {
if (write(fd, buff, 98) < 0) {
perror("write error");
return -1;
}
sleep(1);
}
return 0;
}
阅读(1394) | 评论(0) | 转发(0) |