Subject: Re: Wine & NetBSD?
To: None <tech-kern@netbsd.org>
From: Christos Zoulas <christos@zoulas.com>
List: tech-kern
Date: 11/20/2001 22:29:06
In article <Pine.WNT.4.40.0111201112080.1148-100000@todd>,
Todd Vierling <tv@wasabisystems.com> wrote:
>On Tue, 20 Nov 2001, Bang Jun-Young wrote:
>
>: > > 	mmap((void *)0x50000000, 4096, PROT_READ, 0, fd, 0);
>: > > 	mmap((void *)0x50000000, 4096, PROT_READ, MAP_FIXED, fd, 0);
>: > > 	mmap((void *)0x50000000, 4096, PROT_READ, 0, fd, 0);
>: > > 	mmap((void *)0x50000000, 4096, PROT_READ, MAP_FIXED, fd, 0);
>
>: > A successful
>: > .Fa mmap
>: > deletes any previous mapping in the allocated address range.
>
>: At first I expected that, but the result shows that mmap(2) doesn't
>: act like that: the third mmap call returned 0x50001000, not 0x50000000.
>
>This is because the third mmap call did not specify MAP_FIXED, and as such,
>mmap went to a new location that was not already in use.  There is no
>guaranteed relationship between the first argument to mmap and mmap's result
>if MAP_FIXED is not specified.
>
>Note that some mmap implementations ignore the first argument *completely*
>if MAP_FIXED is not supplied; thus, you should not rely on that first
>argument being heeded at all if MAP_FIXED is not set.  It'd be a perfectly
>valid result, even if suboptimal, for the first mmap call above to return
>0x01234000 rather than 0x50000000.
>
>The Wine people are probably relying on a nonportable Loonixism.  To quote
>the Single Unix Specification, Version 2:
>
>   The format of the call is as follows:
>
>   pa=mmap(addr, len, prot, flags, fildes, off);
>   [...]
>
>   When MAP_FIXED is set in the flags argument, the implementation is
>   informed that the value of pa must be addr, exactly. If MAP_FIXED is set,
>   mmap() may return MAP_FAILED and set errno to [EINVAL]. If a MAP_FIXED
>   request is successful, the mapping established by mmap() replaces any
>   previous mappings for the process' pages in the range [pa, pa + len).
>
>   When MAP_FIXED is not set, the implementation uses addr in an unspecified
>   manner to arrive at pa. The pa so chosen will be an area of the address
>   space that the implementation deems suitable for a mapping of len bytes
>   to the file. All implementations interpret an addr value of 0 as granting
>   the implementation complete freedom in selecting pa, subject to
>   constraints described below. A non-zero value of addr is taken to be a
>   suggestion of a process address near which the mapping should be placed.
>
>   When the implementation selects a value for pa, it never places a mapping
>   at address 0, nor does it replace any extant mapping.
>
>According to this citation, NetBSD is 100% correct in its implementation of
>MAP_FIXED vs. non-MAP_FIXED.

So is linux. Using the address as a hint should not be a problem, as long
as that address has no other mappings. I can see the two POV's clearly.

wine people: It works everywhere else, and it might break if we change it.
Or because of older broken versions of mmap on linux, we don't want to
make any changes.

netbsd people: Well, you depend on completely non portable behavior. If
you *have* to use that particular address, you should specify so. The
code is incorrect because it does not specify MAP_FIXED.

One side of me thinks that we should consider taking the passed address
as a hint, so that we don't have to deal with patching wine, the other
tells me that introducing this behavior will just serve to create more
obscure bugs in the future.

christos