Mailing-List: contact cygwin-help AT cygwin DOT com; run by ezmlm List-Subscribe: List-Archive: List-Post: List-Help: , Sender: cygwin-owner AT cygwin DOT com Mail-Followup-To: cygwin AT cygwin DOT com Delivered-To: mailing list cygwin AT cygwin DOT com Message-ID: <424D9F14.7000209@merrell.org> Date: Fri, 01 Apr 2005 11:20:52 -0800 From: Douglas Merrell User-Agent: Mozilla/5.0 (Windows; U; WinNT4.0; en-US; rv:1.4) Gecko/20030624 Netscape/7.1 (ax) MIME-Version: 1.0 To: cygwin AT cygwin DOT com Subject: Re: Cygwin dll initialization from win32 application Content-Type: text/plain; charset=us-ascii; format=flowed Content-Transfer-Encoding: 7bit On Tue, 11 Mar 2003 15:34:07 -0500, Christopher Faylor wrote: >On Tue, Mar 11, 2003 at 12:48:15PM -0500, Rich LeGrand wrote: >>Hi all, >>This has been discussed before, but I have been unable to find any >>solutions to this problem. >> >>Basically I'm trying to call cygwin functions in the cygwin1.dll >>from a Windows (msvc) application by calling LoadLibrary() and >> GetProcAddress(). >> >>I can see that the cygwin authors have made provision for this >>(or what looks like a provision) with dll_dllcrt0 (a non-cygwin >>initialization function.) But when I call it, it crashes. > >This has been broken for some time. So far no one has stepped >forward to fix the problem in cygwin, so it has remained broken. ---------------------------------------------------------------- I ran into this same problem and investigated a bit. Windows appears to be loading cygwin1.dll differently depending on whether it is: 1) linked into the application and loaded automatically by the Windows loader at runtime (i.e.- compiled with gcc) or 2) loaded dynamically by an application call to LoadLibrary (i.e.- compiled with MSVC++) The only difference in the two loaded modules is one double word at 0x610d2f4c in the .data section (0x610d2f4c memory address, or 0x000d194c file offset in cygwin1.dll). In case 1) the value at the location in memory is exactly as it appears in the raw cygwin1.dll file: 0x00000000. In case 2) the system appears to have changed the value at this location during the LoadLibrary call to 0x00000001. dll_dllcrt0 checks this hardcoded value (see below) as does the lower level function dll_crt0_FP11per_process. If the value is 0x00000000, everything works just fine. If the value is anything other than 0x00000000 (i.e.- in the case where the library is dynamically loaded using LoadLibrary), the application crashes with an AccessViolation. ? What is this hardcoded value? ? Why is the Windows LoadLibrary function changing the value at this location? Test program: int main(int argc, char *argv[]) { HMODULE hModule = LoadLibrary("cygwin1.dll"); /* Use the debugger to inspect the value a 0x610d2f4c */ DebugBreak(); /* If this program is linked with gcc, the Windows loader *will* automatically load cygwin1.dll, so the LoadLibrary call will just return the existing module instance. The value of the long word at 0x610d2f4c will be 0x00000000 as it should be. */ /* If this program is linked with MSVC++, the Windows loader will *not* automatically load cygwin1.dll, so the LoadLibrary call will load it. LoadLibrary will change the value at 0x610d2f4c to 0x0000001.*/ return 0; } Code at entry point dll_dllcrt0: 6100A270 55 push ebp 6100A271 89 E5 mov ebp,esp 6100A273 83 EC 18 sub esp,18h 6100A276 89 5D FC mov dword ptr [ebp-4],ebx 6100A279 8B 5D 0C mov ebx,dword ptr [ebp+0Ch] 6100A27C 85 DB test ebx,ebx 6100A27E 0F 84 9C 00 00 00 je 6100A320 6100A284 8B 53 10 mov edx,dword ptr [ebx+10h] 6100A287 A1 94 B4 0C 61 mov eax,[610CB494] 6100A28C 89 02 mov dword ptr [edx],eax 6100A28E A1 4C 2F 0D 61 mov eax,[610D2F4C] <--***** 6100A293 85 C0 test eax,eax -Doug -- 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/