[fpc-pascal] Re: TProcess.Free - three exceptions in ntdll.dll - only *sometimes*

Bernd Kreuss prof7bit at googlemail.com
Tue Oct 5 20:55:12 CEST 2010


On 04.10.2010 19:23, Bernd Kreuss wrote:

> C0000005 at 7C928FEA in C:\WINDOWS\system32\ntdll.dll
> 
> 7C928FEA seems to be RtlpWaitForCriticalSection() somewhere deep inside
> the windows kernel.

I see this error message now exactly once, immediately *after* the DLL
has been unloaded by the host application.

I'm just looking at the code below (from fpc 2.5.1 trunk,
rtl/win/syswin.inc) and I wonder whether this usage of the critical
section functions might eventually be related to this? (I am still
trying to completely understand this and try to understand why it is
allowed or needed to put these init/done calls in two separate calls of
dllmain, especially this sudden exit in DLL_PROCESS_DETACH caught my eye:


function Dll_entry{$ifdef FPC_HAS_INDIRECT_MAIN_INFORMATION}(const info
: TEntryInformation){$endif FPC_HAS_INDIRECT_MAIN_INFORMATION} :
longbool; [public,alias:'_FPC_DLL_Entry'];
  begin
{$ifdef FPC_HAS_INDIRECT_MAIN_INFORMATION}
     EntryInformation:=info;e
{$endif FPC_HAS_INDIRECT_MAIN_INFORMATION}
     IsLibrary:=true;
     Dll_entry:=false;
     case DLLreason of
       DLL_PROCESS_ATTACH :
         begin
           WinInitCriticalSection(AttachingThread);
           MainThreadIdWin32 := Win32GetCurrentThreadId;

           If SetJmp(DLLBuf) = 0 then
             begin
{$ifdef FPC_HAS_INDIRECT_MAIN_INFORMATION}
               EntryInformation.PascalMain();
{$else FPC_HAS_INDIRECT_MAIN_INFORMATION}
               PascalMain;
{$endif FPC_HAS_INDIRECT_MAIN_INFORMATION}
               Dll_entry:=true;
             end
           else
             Dll_entry:=DLLExitOK;
         end;
       DLL_THREAD_ATTACH :
         begin
           inclocked(Thread_count);

           WinEnterCriticalSection(AttachingThread);
           if Win32GetCurrentThreadId <> MainThreadIdWin32 then
           begin
             { Allocate Threadvars  }
             SysAllocateThreadVars;

             { NS : no idea what is correct to pass here - pass dummy
value for now }
             { passing a dummy is ok, the correct value is read from the
coff header of SysInstance (FK) }
             InitThread($1000000); { Assume everything is idempotent
there, as the thread could have been created with BeginThread... }
           end;

           if assigned(Dll_Thread_Attach_Hook) then
             Dll_Thread_Attach_Hook(DllParam);
           Dll_entry:=true; { return value is ignored }
           WinLeaveCriticalSection(AttachingThread);
        end;
       DLL_THREAD_DETACH :
         begin
           declocked(Thread_count);
           if assigned(Dll_Thread_Detach_Hook) then
             Dll_Thread_Detach_Hook(DllParam);
           { Release Threadvars }
           if Win32GetCurrentThreadId<>MainThreadIdWin32 then
             DoneThread; { Assume everything is idempotent there }
           Dll_entry:=true; { return value is ignored }
         end;
       DLL_PROCESS_DETACH :
         begin
           Dll_entry:=true; { return value is ignored }
		   if MainThreadIDWin32=0 then // already been here.
		     exit;
           If SetJmp(DLLBuf) = 0 then
             FPC_Do_Exit;
           if assigned(Dll_Process_Detach_Hook) then
             Dll_Process_Detach_Hook(DllParam);

           DoneThread;
           { Free TLS resources used by ThreadVars }
           SysFiniMultiThreading;
           WinDoneCriticalSection(AttachingThread);
		   MainThreadIDWin32:=0;
         end;
     end;
  end;



More information about the fpc-pascal mailing list