0

In my linux kernel driver, I need to cast struct inode to struct btrfs_inode.
in order to do it, i looked at implementation of btrfs_getattr.

the code is pretty simple:

#include "/data/kernel/linux-4.1.21-x86_64/fs/btrfs/ctree.h"
#include "/data/kernel/linux-4.1.21-x86_64/fs/btrfs/btrfs_inode.h"
static dev_t get_device_id_btrfs(struct inode* inode){
if (inode != NULL) {
    struct btrfs_inode *btrfsInode;
    btrfsInode = BTRFS_I(inode);
    if (btrfsInode != NULL && btrfsInode->root != NULL) {
        return btrfsInode->root->anon_dev;
    }
}
return 0;
}

in order to compile i must add the headers on top of the function:

#include "/data/kernel/linux-4.1.21-x86_64/fs/btrfs/ctree.h"
#include "/data/kernel/linux-4.1.21-x86_64/fs/btrfs/btrfs_inode.h"

What is the problem ?
I must manually download and include ctree.h and btrfs_inode.h, they are not provided in the kernel-headers package.
On every platform I compile my driver, I have specific VM for the distro/kernel version, so on every VM I usually download package kernel-headers and everything compiles perfectly.

btrfs was introduced in kernel 3.0 above.
Arent the btrfs headers should be there ? do they exist in another package ? maybe fs-headers or something like that ?

Thanks

ilansch
  • 4,784
  • 7
  • 47
  • 96
  • Headers under `fs/btrfs` contains API **private for btrfs driver**: this API is intended to be used *only in the driver's implementation*. So, whole your purpose - `I need to cast struct inode to struct btrfs_inode` - isn't "good", because your are trying to **use other's private API**. In such cases there is no common approaches for get such API. – Tsyvarev Mar 20 '17 at 09:10
  • suse solved this by calling (inode->i_op->getattr(NULL, dentry, &kstat), I wanted to avoid the overhead and simply do the cast.. so i looked in btrfs inode getattr implementation. – ilansch Mar 20 '17 at 09:17
  • How does your code know that the inode belongs to a btrfs file system? – Ian Abbott Mar 21 '17 at 10:06
  • by checking the inode's superblock type – ilansch Mar 21 '17 at 10:39

1 Answers1

0

I solved this by download kernel-sources package and then modified makefile.
This solution may not be recommended, but it is acceptable by me since I build kernel driver that fits only certain kernels/distros which I maintain.
include the following headers:

#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,0,0)
#include <fs/btrfs/ctree.h>
#include <fs/btrfs/btrfs_inode.h>
#endif

and to the Makefile i modified the EXTRA_CFLAGS property "-I/lib/modules/$(KERNEL_HEADERS)/source" :

EXTRA_CFLAGS    +=-D__Linux -std=gnu99 -I/lib/modules/$(KERNEL_HEADERS)/source
ilansch
  • 4,784
  • 7
  • 47
  • 96