[1.7] rebaseall doesn't solve the problem

Charles Wilson cygwin@cwilson.fastmail.fm
Fri Feb 27 21:22:00 GMT 2009


Corinna Vinschen wrote:
>> which means that locale.nls extends all the way down to 0x005E1000, so
>> Cwd.dll can't go at 0x00860000.
> 
> Hm?  Isn't that end_of_mapped_region = mapped_location + mapped_size?

You're right. I was confused by the upside-down chart I was looking at.

> I'm wondering if that's a result of ASLR in Vista.  The document
> http://taossa.com.nyud.net:8080/archive/bh08sotirovdowd.pdf describes,
> starting at page 11, a registry key to influence Vista's ASLR behaviour.
> Does that change the behaviour for you?

It *changes* the behavior, but doesn't fix it.

the default case is key not present, or key present and equal to
anything other than 0 or -1/0xffffffff. In this case, only those DLLs
explicitly marked ASLR-compatible are supposed to be relocated --
subject to the other normal relocation rules.

with the registry key set to 0 (disable ASLR, even if the DLL says it is
ASLR-compatible), I get the same behavior as before: can't remap Cwd.dll.

with the registry key set to -1/0xffffffff (force ASLR for all DLLs), I
get slightly different behavior: can't allocate stack. Presumably this
is because cygwin1.dll itself falls victim to relocation in this
situation (verified this by looking at cygwin1.dll's load address).

> If so, there's nothing Cygwin can do against that.  In the long run,
> only a native fork() implementation would help.

Well, maybe not! From the document you referenced:

    Since Windows relies on relocations instead of position
    independent code, a DLL must be loaded at the same address
    in each process that uses it to allow the physical memory
    used by the DLL to be shared. To facilitate this behaviour,
    a global bitmap called _MiImageBitMap is used to represent
    the address space from 0x50000000 to 0x78000000. The bitmap
    is 0x2800 bits in length with each bit representing 64KB
    of memory. As each DLL is loaded, its position is recorded
    by setting the appropriate bits in the bitmap to mark the
    memory where the DLL is being mapped. When the same DLL
    is loaded in another process, its section object is reused
    and it is mapped at the same virtual addresses.

So, by marking a particular (or all but cygwin1.dll?) DLL as
ASLR-compatibile, we may be able to coerce the Windows runtime loader
into ensuring that the DLLs are loaded at the same memory location for
all concurrent processes (unless the parent has filled up the space from
0x50000000 to 0x78000000, and so is forced to put an ASLR-compatible DLL
somewhere else that is not tracked by _MiImageBitMap).


I wrote a little utility to explicitly mark a DLL as ASLR-compatible.
Using it on Cwd.dll -- the offending one in my situation -- I was able
to eliminate the problem!

I've created it as a patch to the rebase package: 'aslr.exe' is a
separate utility and doesn't actually use the imagebase library.  I've
also modified rebaseall to optionally call it after rebase.  It seems to
work okay; I've manually used it on a dozen or so DLLs -- but I'm still
a little nervous about running it on EVERYTHING in my installation,
since it doesn't quite have the history behind it that rebase does.

Another pair of eyes (or dozen) looking at the code would be nice...

Patch attached. Jason?

--
Chuck
-------------- next part --------------
A non-text attachment was scrubbed...
Name: rebase-2.4.4-1.aslr.patch
Type: application/x-patch
Size: 20601 bytes
Desc: not available
URL: <http://cygwin.com/pipermail/cygwin/attachments/20090227/6724a412/attachment.bin>
-------------- next part --------------
--
Unsubscribe info:      http://cygwin.com/ml/#unsubscribe-simple
Problem reports:       http://cygwin.com/problems.html
Documentation:         http://cygwin.com/docs.html
FAQ:                   http://cygwin.com/faq/


More information about the Cygwin mailing list