यह कुछ ऐसा है जिसे मैंने कुछ दिनों पहले ही खोजा था, मुझे पुष्टि मिली कि यह इस प्रश्न से सिर्फ मेरी मशीन तक सीमित नहीं है ।
विंडोज फॉर्म एप्लिकेशन शुरू करने से इसे रीप्रो करने का सबसे आसान तरीका है, एक बटन जोड़ें और इस कोड को लिखें:
private void button1_Click(object sender, EventArgs e) {
MessageBox.Show("yada");
Environment.Exit(1); // Kaboom!
}
एक्ज़िट () स्टेटमेंट निष्पादित होने के बाद प्रोग्राम विफल हो जाता है । विंडोज फॉर्म पर आपको "विंडो हैंडल बनाने में त्रुटि" मिलती है।
अप्रबंधित डिबगिंग को सक्षम करने से यह स्पष्ट हो जाता है कि क्या चल रहा है। कॉम मोडल पाश को क्रियान्वित करने और एक WM_PAINT संदेश दिया जा करने की अनुमति देता है। यह एक विवादास्पद रूप पर घातक है।
मैंने अभी तक जितने भी तथ्य इकट्ठे किए हैं, वे हैं:
- यह केवल डिबगर के साथ चलने तक सीमित नहीं है। यह भी एक के बिना विफल रहता है। बल्कि खराब तरीके से, WER क्रैश डायलॉग दो बार दिखाता है ।
- इस प्रक्रिया की कड़वाहट से इसका कोई लेना-देना नहीं है। Wow64 परत बहुत कुख्यात है, लेकिन एक AnyCPU बिल्ड उसी तरह क्रैश करता है।
- इसका .NET वर्जन, 4.5 और 3.5 से कोई लेना-देना नहीं है।
- निकास कोड कोई मायने नहीं रखता।
- Exit () कॉल करने से पहले Thread.Sleep () को कॉल करना इसे ठीक नहीं करता है।
- यह विंडोज 8 के 64-बिट संस्करण पर होता है, और विंडोज 7 उसी तरह प्रभावित नहीं होता है।
- यह अपेक्षाकृत नया व्यवहार होना चाहिए, मैंने पहले ऐसा नहीं देखा। मुझे विंडोज अपडेट के माध्यम से कोई प्रासंगिक अपडेट नहीं दिया गया है , यद्यपि कि अपडेट इतिहास मेरी मशीन पर सटीक नहीं है।
- यह घोर तोड़ व्यवहार है। आप AppDomain.UnhandledException के लिए ईवेंट हैंडलर में इस तरह कोड लिखेंगे, और यह उसी तरह क्रैश हो जाएगा।
मुझे विशेष रूप से दिलचस्पी है कि आप इस दुर्घटना से बचने के लिए क्या कर सकते हैं। विशेष रूप से AppDomain.UnhandledException परिदृश्य मुझे स्टंप करता है; .NET प्रोग्राम को समाप्त करने के बहुत सारे तरीके नहीं हैं। कृपया ध्यान दें कि कॉलिंग Application.Exit () या Form.Close () UnhandledException के लिए ईवेंट हैंडलर में मान्य नहीं हैं, इसलिए वे वर्कअराउंड नहीं हैं।
अद्यतन: मेहरदाद ने बताया कि अंतिम धागा समस्या का हिस्सा हो सकता है। मुझे लगता है कि मैं इसे देख रहा हूं और 2 सेकंड के समय के लिए कुछ सबूत भी देख रहा हूं कि सीएलआर अंतिम रूप देने के लिए अंतिम थ्रेड देता है।
अंतिम रूप NativeWindow.ForceExitMessageLoop () के अंदर है। वहाँ एक IsWindow () Win32 समारोह है कि मोटे तौर पर कोड स्थान के साथ मेल खाती है, 0x3c ऑफसेट जब 32-बिट मोड में मशीन कोड को देखते हैं। ऐसा लगता है कि IsWindow () गतिरोध है। मुझे आंतरिक लोगों के लिए एक अच्छा स्टैक ट्रेस नहीं मिल सकता है, लेकिन डिबगर को लगता है कि पी / इनवोक कॉल अभी लौटा है। यह समझाना कठिन है। यदि आप एक बेहतर स्टैक ट्रेस प्राप्त कर सकते हैं तो मैं इसे देखना पसंद करूंगा। मेरी:
System.Windows.Forms.dll!System.Windows.Forms.NativeWindow.ForceExitMessageLoop() + 0x3c bytes
System.Windows.Forms.dll!System.Windows.Forms.NativeWindow.Finalize() + 0x16 bytes
[Native to Managed Transition]
kernel32.dll!@BaseThreadInitThunk@12() + 0xe bytes
ntdll.dll!___RtlUserThreadStart@8() + 0x27 bytes
ntdll.dll!__RtlUserThreadStart@8() + 0x1b bytes
ForceExitMessageLoop कॉल के ऊपर कुछ भी नहीं, अप्रबंधित डिबगर सक्षम है।
This happens on the 64-bit version of Windows 8हंस ने कहा है!
Exit(0)कुछ 64bit Win7 के साथ कुछ समय पहले इस तरह के व्यवहार का सामना कर चुका हूं , बिना किसी समस्या के काम ExitCodeकरने में अब इसका उपयोग करने में मदद नहीं मिली हैProcess.GetCurrentProcess().Kill()