2009-07-16 5 views
0

Nicht sicher, was hier vor sich geht.
Ich habe eine Windows-Konsole App in C geschrieben. Wenn ich es in VS2008 ausführen, läuft es gut. Wenn ich es von der Eingabeaufforderung cmd.exe starte, stürzt es ab, normalerweise in malloc(). Ich vermute, es ist eine Race-Bedingung aufgrund einer nicht übereinstimmenden CRT-Bibliothek.C-basierte Konsole App stürzt ab, wenn von cmd.exe ausgeführt wird, läuft in VS2008 Debugger einwandfrei?

Die App ist einfach.
Ruft die WinHttp-Schicht auf, um eine GET-Anforderung an eine Website zu senden, und schlürft anschließend die Antwort ein. Dieser Teil scheint gut zu funktionieren, aber nach WinHttpReadData, ruft das Programm printf() auf, um die empfangenen Daten auszudrucken, und dort kommt es oft zum malloc-Absturz.

Aber nur außerhalb der Debugger. ????

Ich kompiliere über die Befehlszeile.

c:\vc9\bin\cl.exe /Zi /DEBUG -Ic:\vc9\Include 
      -IC:\WindowsSDK\v6.1\Include HttpGet.c 
      -link /debug /out:HttpGet.exe /SUBSYSTEM:CONSOLE /LIBPATH:c:\vc9\Lib 
       /LIBPATH:C:\WindowsSDK\v6.1\Lib WinHttp.lib 

Ich sehe die Ergebnisse oben, wenn ich kompiliere mit/MT, oder nichts. Wenn ich mit/MD kompiliere, dann hängt es, wenn es im Debugger ausgeführt wird, bei einem Aufruf von free(), und es stürzt in cmd.exe ab (wie bei/MT).

run in    result: /MT   result: /MD 
---------   ------------   ----------- 
VS2008 debugger runs fine    hang in free() (at the end) 
cmd.exe   crash in malloc  crash in malloc 
"VC cmd prompt" crash or hang(spin) ?? 

Einige Fragen -

  1. Ist das unterschiedliche Verhalten wegen der PATH innerhalb VS2008?

  2. Könnte die Ursache sein, dass ich nicht die VC90 Runtime auf meinem Rechner installiert habe?

  3. Ich dachte, dass ich durch die statische Verknüpfung (/ MT) nicht die Anforderung haben müsste, dass die VC90 Runtime installiert werden muss?

  4. Ich verstehe immer noch nicht/NODEFAULTLIB. Ist das relevant?

Ich bin zu Makefiles und Compiler verwendet, und ich weiß, C. Ich weiß nicht, C++, weshalb ich in C schreiben, aber ich verstehe nicht, alle Launen des CRT unter Windows. Kann jemand dieses Geheimnis aufklären?

Antwort

3

Normalerweise, wenn ich gesehen habe, dass etwas im Debugger funktioniert, aber nirgendwo sonst, liegt das an nicht initialisiertem Speicher. Der Debugger ist "nett genug", um Speicher für Sie zu löschen, als ob Ihnen das einen Gefallen tut.

Die zweite Möglichkeit ist ein Pufferüberlauf, und der Debugger veranlasst den Speicherort Ihrer mallocs, sich genug zu bewegen, um es zu vermeiden. Ich würde vermuten, dass dieser Fehler bei einem malloc auftaucht; Sie könnten die Malloc-Kette korrumpieren.

Eine andere Möglichkeit, die herausragt, ist eine Art Race Condition, und der Debugger ändert das Timing so weit, dass Sie damit durchkommen.

+0

hmm, ok. Gute Ideen. Ich habe C# zu lange gemacht ... – Cheeso

+0

Es ist ein bisschen schwierig, weil OP unter Windows ist, aber das Ausführen Ihres Programms unter Valgrind wird die Speicherfehler abfangen, die der Debugger versteckt. Glibc markiert auch alle unbenutzten Speicher mit einem speziellen Muster, wenn 'MALLOC_PERTURB_' gesetzt ist, und jedes andere Muster als' NULL' ist gut zum Erfassen von Fehlern - ich weiß nicht, ob es eine Entsprechung in Windows 'CRT gibt. – ephemient

+0

Ich hatte ein paar kleine Pufferüberläufe. Schlampig schlampig schlampig. Sehen Sie, welche Codierung in .NET Sie bekommen wird?Trotzdem danke für die Erinnerung. – Cheeso

Verwandte Themen