LogHelp_TerminateOnAssert nedir?

Nov 04 2020

On yıl öncesine ait benzer bir soru var, ancak iyi bir cevap yoktu - umarım o zamandan beri işler değişti.

.NET 4.72'ye dayalı oldukça çok iş parçacıklı bir Winforms uygulamam var. Process Explorer Threads görünümüyle bakıyorum ve çok sayıda clr.dll!LogHelp_TerminateOnAssert+0x6835tür çağrısı var. Symbols yolunu ayarladım ama bu benim için hiçbir şeyi gerçekten netleştirmedi.

Uygulamanın bir dökümünü aldım ve DebugDiag ve WinDbg üzerinden çalıştırdım ve göze çarpan şüpheli bir şey görmedim.

Yani sorularım:

  • Çok sayıda LogHelp_TerminateOnAssert çağrısıyla ilgilenmeli miyim?
  • Uygulama bellek sızdırıyor mu?
  • Uygulamayı Visual Studio'da çalıştırdığımda filtrelemeyen aşırı sayıda özel durum var mı?

Buradaki kodumdan tek giriş !get_FrameReceivedve bu iş parçacığı için yığın aşağıdaki gibidir:

En çok döngüye sahip iş parçacığı için yığın şu şekildedir:

Yanıtlar

2 ThomasWeller Nov 05 2020 at 21:01

Büyük ofsetler

clr.dll!LogHelp_TerminateOnAssert+0x6835

bu yöntemdeki gerçek yürütmenin başlangıcından 0x6835 = 26661 bayt uzakta olduğu anlamına gelir. Bir yöntemin bu kadar büyük olması pek olası değildir. (@Blabb'ın işaret ettiği gibi, bu 1 baytlık bir yöntemdir).

Genellikle sembolleri doğru bir şekilde ayarlamadığınızda (bağlantılı orijinal soruda olduğu gibi), ancak bunu düzelttiğinizde görürsünüz.

Muhtemelen Microsoft, clr.dllözel olanları değil , yalnızca genel sembollerini yayınlamıştır . Bu durumda, yalnızca son bilinen genel yöntemi göreceksiniz.

Başlangıç ​​adresi

Sütunun "Başlangıç ​​adresi" olarak adlandırıldığını lütfen unutmayın. İşlem Gezgini, yığındaki ilk girişi gösterecektir.

Yani her şeyin başladığı yer burası. Her şeyin bittiği yerin burası olduğundan endişeleniyor gibisin.

Not: Başlangıç ​​adresi görüntülenirken RtlUserThreadStartve gibi bilinen bazı dahili yöntemler BaseThreadInitThunkatlanacaktır. Aksi takdirde muhtemelen hepsi aynı görünürdü.

İş parçacığının gerçekte yaptığı şey listenin en üstünde, yani ZwRemoveIoCompletionbazı IO işlemi yapıyor gibi görünüyor.

Sorularınız

Çok sayıda LogHelp_TerminateOnAssert çağrısıyla ilgilenmeli miyim?

Hayır. Bunlar, iyi bir şeyin başlangıç ​​noktasıdır. GetQueuedCompletionStatus()Bakışlar IO Tamamlama Limanlar (IOCP) sizin için bazı IO ve .NET oluyor kullanır var gibi.

Uygulama bellek sızdırıyor mu?

Bunu çağrı yığınlarına bakarak söylemezsiniz. Bunu zamanla hafızaya bakarak anlatırsın.

Devam eden çok fazla ağ GÇ'niz varsa ve ağ buna ayak uyduramıyorsa, .NET'in kuyrukta giderek daha fazla öğesi olabilir, bu nedenle bellek sızıntısı gibi görünebilir .

Uygulamayı Visual Studio'da çalıştırdığımda filtrelemeyen aşırı sayıda özel durum var mı?

Bunu çağrı yığınından da söylemezsiniz. sxe clrVisual Studio'ya güvenmiyorsanız, bir hata ayıklayıcı (örn. WinDbg) ekler ve istisnaları (gibi ) kontrol edersiniz.

2 blabb Nov 05 2020 at 18:43

sürüm derlemesinde tüm bu iddialar basit bir ret halinde derlenir.

ifdef ( debug ) { function body here } elseif { ret } endif

bu yüzden bu kadar büyük ofseti olan semboller sahte

bu nedenle, mantıklı bir çağrı yığını için bu adresin gerçek sembollerini yüklemeniz gerekebilir.

clr 4.0.30319 clr.dll'deki işlevin boyutunu görebilirsiniz. sadece 1 bayt

0:000> x /v /t clr!LogHelp_TerminateOnAssert
pub func   100115a0             0 <NoType> clr!LogHelp_TerminateOnAssert (<no parameter info>)
0:000> .fnent clr!LogHelp_TerminateOnAssert
Debugger function entry 01bad5e0 for:
(100115a0)   clr!RtlUnwindCallback   |  (100115a1)   clr!memset
Exact matches:
    clr!RtlUnwindCallback (void)
    clr!_TlgDefineProvider_annotation__Tlgg_hClrProviderProv (void)

OffStart:  000115a0
ProcSize:  0x1
Prologue:  0x0
Params:    0n0 (0x0 bytes)
Locals:    0n0 (0x0 bytes)
Registers: 0n0
0:000> u clr!LogHelp_TerminateOnAssert l1
clr!RtlUnwindCallback:
100115a0 c3              ret