Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 6 Aug 2003 13:45:37 -0700
From:      "Luoqi Chen" <lchen@briontech.com>
To:        "Ed L Cashin" <ecashin@uga.edu>, <hackers@freebsd.org>
Subject:   RE: COW and mprotect on non-shared memory
Message-ID:  <AHEKICEOIHLOGINAFIINIEDICBAA.lchen@briontech.com>
In-Reply-To: <87he4uzr1z.fsf@uga.edu>

next in thread | previous in thread | raw e-mail | index | archive | help
> For that reason, when you mprotect an area of non-shared, anonymous
> memory to no access and then back to writable, Linux has no way of
> knowing that the memory wasn't set for COW before you make it
> unwritable.  It goes ahead and makes all the pages in the area COW.
> 
> That means that if I do this:
> 
>     for (i = 0; i < n; ++i) {
>       assert(!mprotect(p, pgsiz, PROT_NONE));
>       assert(!mprotect(p, pgsiz, PROT_READ|PROT_WRITE|PROT_EXEC));
>       p[i] = i & 0xff;
>     }
> 
> ... I get n minor page faults!  Pretty amazing, but I guess they
> figured nobody does that.  
> 
> More surprising is that the same test program has the same behavior on
> FreeBSD.  (At least, the "/usr/bin/time -l ..." output shows the
> number of page reclaims increasing at the same rate that I increase
> the value of n in the loop.)  
> 
> I thought that in FreeBSD any COW area would have its own vm_map_entry
> with the MAP_ENTRY_COW bit set.  That way, you could run this test
> without any minor faults at all.  Now I suspect I was incorrect.
> Could anyone help clarify the situation for me?
> 
> Thanks.
> 
> -- 
> --Ed L Cashin            |   PGP public key:
>   ecashin@uga.edu        |   http://noserose.net/e/pgp/
> 
The first mprotect() removes the physical mapping from the page table,
the second mprotect() doesn't do anything because the mapping isn't
there. So when the page is accessed, a fault is needed to insert the
mapping back to the page table.

-lq



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?AHEKICEOIHLOGINAFIINIEDICBAA.lchen>