RtlCaptureStackBackTrace gibt keine Frames zurück

Cromon

Erfahrenes Mitglied
Hallo zusammen!

Da in meiner Applikation viel Verkehr zwischen verwaltetem und unverwaltetem Code herrscht brauche ich in .NET auch die Möglichkeit Frames vom Stack zu bekommen, die im unverwalteten Teil liegen. In ganz unverwalteten Projekten habe ich dazu immer RtlCaptureStackBackTrace verwendet (problemlos). Nun habe ich das also auch hier versuchen wollen und folgende Signatur erstellt:
C#:
        [DllImport("ntdll.dll", SetLastError = true)]
        private static extern ushort RtlCaptureStackBackTrace(uint framesToSkip, uint framesToCapture, IntPtr BackTrace, ref uint hash);

Nun ist es jedoch so, dass der Aufruf der Funktion leider immer 0 zurückgibt, was einen Fehler andeuten würde. Genau so gibt aber auch Marshal.GetLastWin32Error() tollerweise 0 zurück, was wiederum bedeutet, dass alles in Ordnung ist...

Der Aufruf:
C#:
                uint[] frames = new uint[64];
                IntPtr arr = IntPtr.Zero;
                ushort numFrames = 0;
                fixed (uint* fp = frames)
                {
                    arr = new IntPtr(fp);
                    uint hash = 0;
                    numFrames = RtlCaptureStackBackTrace(0, 60, arr, ref hash);
                }

Ich schaue mir momentan den Aufbau der Funktion in der ntdll an und werde mal schauen, was die Funktionen intern dazu meinen, bzw wo das ganze fehlschlägt (OllyDbg).

Hat vielleicht jemand von euch noch eine Idee?

Gruss und Dank
Cromon


PS: Ich halte euch auf dem laufenden, wenn ich etwas entdecken sollte.
 
Also mein Problem ist folgendes:
RtlCaptureStackBackTrace ruft RtlWalkFrameChain auf, welches wiederum (in meinem Fall) RtlWalk32BitStack aufruft. Das Problem taucht dann in der Funktion auf. RtlpStkIsPointerInDllRange gibt nur für das Frame RtlCaptureStackBackTrace true zurück, sobald ein Frame meines Codes dran wäre gibt das 0 zurück.
 
Mittlerweile hat sich das Problem offenbart. Anscheinend wird im Loader von komplett verwalteten DLLs LdrLoadDll bzw. LdrpLoadOrMapDll nicht aufgerufen und somit dann auch RtlpStkMarkDllRange. Dadurch schlägt später die Abfrage in der ntdll fehl und RtlCaptureStackBacktrace schlägt fehl. Meiner Meinung nach ist dies ein Fehler. Die DllRange in der ntdll wird nur von RtlpIsPointerInRange abgefragt. Diese Finktion wiederum wird nur von Stackwalkfunktionen verwendet. In dieser Beziehung gehört die DLL auf jeden Fall in die gültigen Ranges. Arbeite ich direkt mit dem Stackpointer kann ich mich super durch den Stack angeln. Alternativ funktioniert auch StackWalk64.
 
Zurück