What are the implications of linux __user macros?

I was hoping someone could explain the nuances of the __user macro used in the linux kernel source.

First of all, the macro:

# define __user __attribute__((noderef, address_space(1))) 

Now, after some searching on Google, I read that this macro allows you to designate a pointer as belonging to the user's address space and that it should not be dereferenced.

Perhaps I am missing some obvious facts, but can someone explain the consequences of such a macro? For example, what is a good example of where this macro will be useful? Again, forgive me if I missed something obvious.

To add this to some context, I came across a macro, studying some USB code (linux / usbdevice_fs.h). I am only looking for a general understanding of these macros (or other similar ones) in the kernel.

Thanks for watching!

+43
c macros linux-kernel kernel
Dec 23 '10 at 18:46
source share
3 answers

It allows you to use tools like sparse to tell kernel developers that they may be using an untrusted pointer (or a pointer that might be invalid in the current virtual address mapping).

+33
Dec 23 '10 at 18:59
source share

I think __user places pointers to user space and tells the developer / system not to trust him. If the user gives you an "invalid" pointer, then the kernel tries to reference it (note that the kernel can refer everywhere), and it can ruin its own space.

For example, in "read" (you have usbdevice_fs.h), a buffer (__user) should be provided for you to write the result. So you need to use copy_to_user, but not memcopy, strcpy or something like that.

Note. This is not a formal definition / description, but the only part that I know of.

+27
Dec 30 '10 at 10:08
source share

The __user macro __user defined using some other macros, such as __force / __kernel , etc. in the compiler.h header file. In fact, they are not used by traditional compilers, including GCC / ICC, etc. But this is useful for static kernel analysis tools such as sparse ones (more details here: Sparse - Linux Kernel Newbies). When you specify macros like __user / __kernel / __force , etc., It retains special meaning for sparse ones. On the Linux kernel mailing list, Linus Torvalds explains its use as follows:

This is important to remember: for gcc, sparse annotations are pointless. They can still be useful only to tell the programmer that โ€œhey, this pointer you received was not a normal pointerโ€ in a fairly readable way, but, in the end, if you do not use a sparse language, they actually do nothing.

HOWEVER. When you use parsing, this is a completely different matter. For the "rare" that "__iomem" makes a lot of sense:

 # define __iomem __attribute__((noderef, address_space(2))) 

those. "iomem" means two separate things: this means that a sparse one must complain

if the pointer is ever dereferenced (it is the "noderef" pointer) directly, and it is in "address space 2" in contrast to the usual address space (0).

Now that means a sparse one will complain if such a pointer is ever passed to a function that wants a regular pointer (because it's not a regular pointer, and you obviously shouldn't do things like "strcmp ()" and so .d. on it), and the sparse one will also complain if you try to transfer it to another pointer in a different address space.

+1
Jun 28 '16 at 23:28
source share



All Articles