1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99
|
/*
* netsniff-ng - the packet sniffing beast
* Copyright 2009, 2010 Daniel Borkmann.
* Copyright 2014 Tobias Klauser
* Subject to the GPL, version 2.
*/
#include <stdio.h>
#include <stdint.h>
#include <netinet/in.h>
#include <linux/if_ether.h>
#include "proto.h"
#include "dissector_eth.h"
#include "pkt_buff.h"
#include "oui.h"
static inline bool is_multicast_ether_addr(const uint8_t *mac)
{
return mac[0] & 0x01;
}
static inline bool is_broadcast_ether_addr(const uint8_t *mac)
{
return (mac[0] & mac[1] & mac[2] & mac[3] & mac[4] & mac[5]) == 0xff;
}
static const char *ether_lookup_addr(uint8_t *mac)
{
if (is_multicast_ether_addr(mac)) {
if (is_broadcast_ether_addr(mac))
return "Broadcast";
else
return "Multicast";
}
/* found no matching address, so look up the vendor from OUI */
return lookup_vendor_str((mac[0] << 16) | (mac[1] << 8) | mac[2]);
}
static void ethernet(struct pkt_buff *pkt)
{
char *type;
uint8_t *src_mac, *dst_mac;
struct ethhdr *eth = (struct ethhdr *) pkt_pull(pkt, sizeof(*eth));
if (eth == NULL)
return;
src_mac = eth->h_source;
dst_mac = eth->h_dest;
tprintf(" [ Eth ");
tprintf("MAC (%.2x:%.2x:%.2x:%.2x:%.2x:%.2x => ",
src_mac[0], src_mac[1], src_mac[2],
src_mac[3], src_mac[4], src_mac[5]);
tprintf("%.2x:%.2x:%.2x:%.2x:%.2x:%.2x), ",
dst_mac[0], dst_mac[1], dst_mac[2],
dst_mac[3], dst_mac[4], dst_mac[5]);
tprintf("Proto (0x%.4x", ntohs(eth->h_proto));
type = lookup_ether_type(ntohs(eth->h_proto));
if (type)
tprintf(", %s%s%s", colorize_start(bold), type, colorize_end());
tprintf(") ]\n");
tprintf(" [ Vendor ");
tprintf("(%s => %s)", ether_lookup_addr(src_mac), ether_lookup_addr(dst_mac));
tprintf(" ]\n");
pkt_set_proto(pkt, ð_lay2, ntohs(eth->h_proto));
}
static void ethernet_less(struct pkt_buff *pkt)
{
uint8_t *src_mac, *dst_mac;
struct ethhdr *eth = (struct ethhdr *) pkt_pull(pkt, sizeof(*eth));
if (eth == NULL)
return;
src_mac = eth->h_source;
dst_mac = eth->h_dest;
tprintf(" %s => %s ",
lookup_vendor_str((src_mac[0] << 16) | (src_mac[1] << 8) |
src_mac[2]),
lookup_vendor_str((dst_mac[0] << 16) | (dst_mac[1] << 8) |
dst_mac[2]));
tprintf("%s%s%s", colorize_start(bold),
lookup_ether_type(ntohs(eth->h_proto)), colorize_end());
pkt_set_proto(pkt, ð_lay2, ntohs(eth->h_proto));
}
struct protocol ethernet_ops = {
.key = 0,
.print_full = ethernet,
.print_less = ethernet_less,
};
|