Re: How does __do_clear_user() works?

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On 01-08-08 10:41, Prasad Joshi wrote:

Here is the code for __do_clear_user, I am not getting how does it work. Can any one please explain?

#define __do_clear_user(addr,size)                                      \
do {                                                                    \
        int __d0;                                                       \
        might_sleep();                                                  \
        __asm__ __volatile__(                                           \
                "0:     rep; stosl\n"                                   \

The straightforward assembly bit -- I assume you know wat a "rep stosd" ("rep; stosl" in at&t braindamage) does.

Setting up eax (as 0), ecx (size / 4) and edi (addr) is left to GCC inline assembly syntax at (*) below.

("es" is already set correctly; it never changes).

                "       movl %2,%0\n"                                   \
                "1:     rep; stosb\n"                                   \

We have a few bytes left if the size wasn't divisable by 4, so now store the remaining bytes. register al (low byte of eax) is still 0, edi is correct from previous rep stosd and ecx is loaded with size & 3.

                "2:\n"                                                  \
                ".section .fixup,\"ax\"\n"                              \
                "3:     lea 0(%2,%0,4),%0\n"                            \
                "       jmp 2b\n"                                       \
                ".previous\n"                                           \
                _ASM_EXTABLE(0b,3b)                                     \
                _ASM_EXTABLE(1b,2b)                                     \

This is the fun bit. This is the so called "fixup" code which basically means that rather than try and check if a page is present (swapped in) in advance you just go ahead and access it and let it fault if it isn't, after which you fix it up.

Please see Documentation/exception.txt for further information.

                : "=&c"(size), "=&D" (__d0)                             \
                : "r"(size & 3), "0"(size / 4), "1"(addr), "a"(0));     \

(*)

This is the GCC inline assembly syntax bit. You can learn about it in "info gcc", C Extensions, Extended ASM. Basically, ecx and edi are output operands stored back into "size" and "__d0", "size / 4" and "addr" are input operands put in those same registers, eax is set to 0 and the remainder is setup as operand 2.

So we have 3 things here

- AT&T syntax which might confuse you if you're used to reading Intel
  CPU manuals (and should piss you off even if it doesn't confuse you).

- GCC inline assembly syntax which for all it's obscurity is actually
  not all bad.

- Linux fixup code which obscures things further.

Hope this helps seperating the 3.

Rene.

--
To unsubscribe from this list: send an email with
"unsubscribe kernelnewbies" to ecartis@xxxxxxxxxxxx
Please read the FAQ at http://kernelnewbies.org/FAQ


[Index of Archives]     [Newbies FAQ]     [Linux Kernel Mentors]     [Linux Kernel Development]     [IETF Annouce]     [Git]     [Networking]     [Security]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux RAID]     [Linux SCSI]     [Linux ACPI]
  Powered by Linux