X-Spam-Check-By: sourceware.org Date: Thu, 24 Aug 2006 18:53:57 -0400 (EDT) From: Igor Peshansky Reply-To: cygwin AT cygwin DOT com To: Pierre Baillargeon cc: cygwin AT cygwin DOT com Subject: Re: no message or dialog when a DLL is missing In-Reply-To: <44EDF86F.6030107@innobec.com> Message-ID: References: <44ECC152 DOT 3020503 AT innobec DOT com> <44EDA26C DOT 6000603 AT innobec DOT com> <44EDF86F DOT 6030107 AT innobec DOT com> MIME-Version: 1.0 Content-Type: TEXT/PLAIN; charset=US-ASCII Mailing-List: contact cygwin-help AT cygwin DOT com; run by ezmlm Precedence: bulk List-Unsubscribe: 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 On Thu, 24 Aug 2006, Pierre Baillargeon wrote: > Ok, first I want to show you the minimal test-case I built. Using Visual > Studio 8, I created a solution containing two projects: a Win32 console > application and a Win32 DLL. I deleted all the generated stuff and > replaced them with a single file per project. > > The console application project is called NoDLL and its file is called > NoDLL.c: > > __declspec( dllimport ) void __stdcall cant_touch_this(); > > int main(int argc, char* argv[]) > { > cant_touch_this(); > printf("World!\n"); > return 0; > } > > The DLL project is called Missing and its file is called Missing.c: > > __declspec( dllexport ) void __stdcall cant_touch_this() > { > printf("Hello\n"); > } > > The console project is set to depend on the DLL project: Project menu, > Project Dependencies... menu item, select the console application in the > drop down combo-box, check mark the DLL in the list box below it. Now > the console depends on the DLL and will be linked with its .lib file. > > Now, after building the project, I have NoDLL.exe and Missing.dll in the > same directory. > > In a bash shell started from a shortcut (i.e. bash inside cmd.exe), I > start NoDLL.exe. I get Hello World! as expected. I move the DLL > elsewhere, now the program does nothing and the exit code (echo $?) is > 128. > > If I start the program right then in another Windows cmd.exe, i get a > nice error dialog saying "This application has failed to start because > Missing.dll was not found. Re-installing the application may fix this > problem." With the title "NoDLL.exe - Unable To Locate Component". Same > thing if I double click NoDLL.exe from Windows Explorer. > > This difference in behavior was my reason to write in. Thanks for the minimal test case. I was able to reproduce your problem with gcc-compiled executable and DLL (both with and without -mno-cygwin). See below for some analysis. > Now, about cygcheck. Two cases. > > 1. If the current directory is where NoDLL.exe and Missing.dll are. In > this case, I get: > > .\NoDLL.exe > .\Missing.dll > C:\WINDOWS\system32\KERNEL32.dll > C:\WINDOWS\system32\ntdll.dll > > or > > .\NoDLL.exe > Error: could not find Missing.dll > C:\WINDOWS\system32\KERNEL32.dll > C:\WINDOWS\system32\ntdll.dll Right. That was actually a false lead. > 2. If the current directory is *not* where NoDLL.exe and Missing.DLL > are. In the case, I always get: > > /path/to/where/the/program/is/NoDLL.exe - Cannot open > > *Even* if Missing.DLL is present next to NoDLL.exe and NoDLL.exe and can > be launchedproperly in bash! This one I can't reproduce. I always get the right output -- do you, perhaps, have an older cygcheck? > Sorry, I was not able to rapidly make the DLL and executable with gcc. gcc -mno-cygwin -shared -o Missing.dll Missing.c > trying only to build the program, with the DLL already built by MSVC, > using "gcc -mno-cygwin -L./Debug -lMissing NoDLL.c", resulted in > "/cygdrive/c/Temp/ccMLHNI5.o:NoDLL.c:(.text+0x2b): undefined reference > to `__imp__cant_touch_this AT 0'". I used gcc -mno-cygwin -o NoDll.exe NoDll.c Missing.dll to build the executable with the embedded DLL reference. Now, the analysis: according to strace, the spawning process (e.g., the shell) does receive the Windows exception C0000135 (a.k.a. STATUS_DLL_NOT_FOUND), handles it, and uses it to set exit code to 0x35. My guess is that neither cmd.exe nor the Windows launcher install a handler for the exceptions, and thus the default Windows handler (which creates a pop-up) is used. I'm not sure what the dictated POSIX behavior is in this case -- perhaps Cygwin is doing the right thing in intercepting the exception. In any case, if I were to try fixing it, I'd start in spawn_guts() and work my way from there to the place where the exception handler is installed, then create a patch that removes the handling for this exception, and then read for instructions on how to contribute this patch to the Cygwin codebase (that is not to say that it will be immediately accepted, but it will certainly be thoughtfully considered). HTH, Igor -- http://cs.nyu.edu/~pechtcha/ |\ _,,,---,,_ pechtcha AT cs DOT nyu DOT edu | igor AT watson DOT ibm DOT com ZZZzz /,`.-'`' -. ;-;;,_ Igor Peshansky, Ph.D. (name changed!) |,4- ) )-,_. ,\ ( `'-' old name: Igor Pechtchanski '---''(_/--' `-'\_) fL a.k.a JaguaR-R-R-r-r-r-.-.-. Meow! "Las! je suis sot... -Mais non, tu ne l'es pas, puisque tu t'en rends compte." "But no -- you are no fool; you call yourself a fool, there's proof enough in that!" -- Rostand, "Cyrano de Bergerac" -- 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/