Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

IP-address from sk_buff

I am writing a kernel module which registers a netfilter hook. I am trying to get the ip address of the caller by using the sk_buff->saddr member. Is there a way I can get the IP in human readable i.e. x.x.x.x format?

I found the function inet_ntop() but it doesn't seem to be available in kernel headers. How do I convert \xC0\xA8\x00\x01 to 192.168.0.1 ?

like image 245
Rohit Avatar asked Feb 25 '09 04:02

Rohit


2 Answers

You should use the %pI4 extended format specifiers provided by printk():

printk(KERN_DEBUG "IP addres = %pI4\n", &local_ip);
like image 147
Cong Wang Avatar answered Sep 18 '22 18:09

Cong Wang


There are two macros defined in include/linux/kernel.h

NIPQUAD for ipv4 addresses and NIP6 for ipv6 addresses.

#define NIPQUAD(addr) \
    ((unsigned char *)&addr)[0], \
    ((unsigned char *)&addr)[1], \
    ((unsigned char *)&addr)[2], \
    ((unsigned char *)&addr)[3]

#define NIP6(addr) \
    ntohs((addr).s6_addr16[0]), \
    ntohs((addr).s6_addr16[1]), \
    ntohs((addr).s6_addr16[2]), \
    ntohs((addr).s6_addr16[3]), \
    ntohs((addr).s6_addr16[4]), \
    ntohs((addr).s6_addr16[5]), \
    ntohs((addr).s6_addr16[6]), \
    ntohs((addr).s6_addr16[7])

There are ample examples in the kernel sources that make use of these to print ip addresses in human-readable format. For instance:

printk(KERN_DEBUG "Received packet from source address: %d.%d.%d.%d!\n",NIPQUAD(iph->saddr));

Hope this helps.

like image 31
anbhat Avatar answered Sep 22 '22 18:09

anbhat