Re: Change in functionality of futex() system call.

From: Darren Hart
Date: Fri Jun 24 2011 - 20:00:57 EST


Hi Eric,

I'm finally getting time to review this in depth and try to help Shawn
get his fix upstream. Trying to make sure I have all the facets of this
straight in my head... or on paper at least ;-)

On 06/06/2011 11:27 AM, Eric Dumazet wrote:
> Le lundi 06 juin 2011 Ã 20:23 +0200, Peter Zijlstra a Ãcrit :
>
>>
>> That's really not the point, what do we do when the COW happens during
>> the FUTEX_WAIT? At that point the process vaddr changes mapping and we
>> cannot continue the wait on the old page, since that would expose
>> invisible information, nor can we switch to the new page since we queued
>> on the old page.
>>
>> Therefore we have to force the COW and queue on the private copy, it
>> really is the only semi sane semantic.
>
> The point is we dont necessarly have to COW the page. If you attempt
> this COW, you shoot on user that did not expect to have a COW.
>
> Take this program : COW is not allowed, still this worked on 2.6.18 (it
> waits until another process change the value in file and call
> futex_wait())
>
> Using PROT_READ | PROT_WRITE instead of PROT_READ was OK too.
>
> (If we use PROT_READ | PROT_WRITE, then after your patch, program doesnt
> work anymore since this process gets a private page after your hidden
> COW : It'll wait forever)


As I understand MMAP(2), this is working due to undefined behavior as
Stephen pointed out earlier:

"It is unspecified whether changes made to the file after the mmap()
call are visible in the mapped region."

I don't think we are under any obligation to keep that working.

--
Darren

>
> #include <errno.h>
> #include <fcntl.h>
> #include <stdint.h>
> typedef uint32_t u32; // for futex.h
> #include <linux/futex.h>
> #include <sys/mman.h>
> #include <sys/syscall.h>
> #include <unistd.h>
>
>
> int main(int argc, char *argv[]) {
> int fd, *futex, rc, val = 42;
>
> fd = open("/tmp/futex_test", O_RDWR|O_CREAT, 0644);
> write(fd, &val, 4);
> futex = (int *)mmap(0, sizeof(int), PROT_READ, MAP_PRIVATE, fd, 0);
> rc = syscall(SYS_futex, futex, FUTEX_WAIT, val, 0, 0, 0);
> printf("rc=%d errno=%d\n", rc, errno);
> }
>
>
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
> the body of a message to majordomo@xxxxxxxxxxxxxxx
> More majordomo info at http://vger.kernel.org/majordomo-info.html
> Please read the FAQ at http://www.tux.org/lkml/

--
Darren Hart
Intel Open Source Technology Center
Yocto Project - Linux Kernel
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/