Abhishek Sagar Abhishek Sagar - 3 months ago 15
Linux Question

unable to fetch mac address from net_device in kernel module

This is my hook function

unsigned int
my_packet_pass_through_hook(const struct nf_hook_ops *ops,
struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
int (*okfn)(struct sk_buff*)){


which i have registered in PREROUTING and POSTROUTING stages. i just dump the net_device information in this function.
In PREROUTING stage, i am dumping const struct net_device *in whereas in POSTROUTING stage i am dumping const struct net_device *out net_devoce structure.

In both the cases, i am not able to print the MAC address of the device.

printk(KERN_ALERT " Mac Addr = %s\n", iif->dev_addr);
printk(KERN_ALERT " Broadcast Addr = %s\n", iif->broadcast);


output

Apr 28 19:56:21 node2 kernel: [ 466.344567] Mac Addr =

Apr 28 19:56:21 node2 kernel: [ 466.344568] Broadcast Addr = ▒▒▒▒▒▒

pls note, i am running my module on node 2 which routes the pings to node3 from node1. So, all packets are forwarded.I am only reading the fields of the packet and printing it without tempering it in anyway. So, pings are successful.

Also, could anyone pls enlighten me what is okfn fn pointer and its usage ?

Many thanks.

Answer

The field is right, dev_addr is the hardware address, and broadcast holds the hardware broadcast address, but you cannot print them like a string! They are an array of unsigned chars, where each char holds a octet of the mac address. Use the specific modifier of printk designed for mac address instead:

printk(KERN_ALERT "   Mac Addr         = %pMF\n", iif->dev_addr);
printk(KERN_ALERT "   Broadcast  Addr  = %pMF\n", iif->broadcast);

You can find other formats in the printk docs:

http://lxr.free-electrons.com/source/Documentation/printk-formats.txt#L136