Technische Details
0 [main] us 0 init_cheap: VirtualAlloc pointer is null, Win32 error 487
AllocationBase 0x0, BaseAddress 0x68570000, RegionSize 0x2A0000, State 0x10000
PortableGit\bin\bash.exe: *** Couldn't reserve space for cygwin's heap, Win32 error 0
Dieses Symptom an sich hat nichts mit Image-Basen ausführbarer Dateien, beschädigten Cygwins gemeinsam genutzten Speicherabschnitten, widersprüchlichen Versionen von DLLs usw. zu tun.
Es ist Cygwin-Code, der keinen ~ 5 MB großen Speicherblock für seinen Heap an dieser festen Adresse 0x68570000 zuweisen kann, während dort anscheinend nur ein Loch mit einer Größe von ~ 2,5 MB verfügbar war. Der relevante Code ist in der msysgit-Quelle zu sehen .
Warum ist dieser Teil des Adressraums nicht frei?
Es kann viele Gründe geben. In meinem Fall wurden einige andere Module an einer widersprüchlichen Adresse geladen:
Die letzte Adresse wäre ungefähr 0x68570000 + 5 MB = 0x68C50000, aber es gibt diese WOW64-bezogenen DLLs, die ab 0x68810000 geladen werden und die Zuordnung blockieren.
Wenn eine gemeinsam genutzte DLL vorhanden ist, versucht Windows im Allgemeinen, diese in allen Prozessen unter derselben virtuellen Adresse zu laden, um eine gewisse Umzugsverarbeitung zu sparen. Es ist nur eine Frage des Peches, dass diese Systemkomponenten diesmal irgendwie an einer widersprüchlichen Adresse geladen wurden .
Warum ist Cygwin in deinem Git?
Weil Git eine umfangreiche Suite ist, die aus einigen einfachen Befehlen und vielen hilfreichen Dienstprogrammen besteht und hauptsächlich auf Unix-ähnlichen Systemen entwickelt wurde. Um es ohne massives Umschreiben erstellen und ausführen zu können, ist mindestens eine teilweise Unix-ähnliche Umgebung erforderlich.
Um dies zu erreichen, haben die Leute MinGW und MSYS erfunden - eine minimale Anzahl von Build-Tools, um Programme unter Windows auf Unix-ähnliche Weise zu entwickeln. MSYS enthält auch eine gemeinsam genutzte Bibliothek, msys-1.0.dll
die bei einigen Kompatibilitätsproblemen zwischen den beiden Plattformen zur Laufzeit hilft. Und viele Teile davon wurden Cygwin entnommen, weil dort bereits jemand die gleichen Probleme lösen musste.
Es ist also nicht Cygwin, sondern die Laufzeit-DLL von MinGW, die sich hier komisch verhält.
In Cygwin hat sich dieser Code seit MSYS 1.0 stark verändert - die letzte Commit-Nachricht für diese Datei lautet "Import Cygwin 1.3.4" aus dem Jahr 2001!
Sowohl das aktuelle Cygwin als auch die neue Version von MSYS - MSYS2 - verfügen bereits über eine unterschiedliche Logik, die hoffentlich robuster ist. Es sind nur alte Versionen von Git für Windows, die noch mit dem alten kaputten MSYS-System erstellt wurden.
Saubere Lösungen:
- Installieren Sie Git für Windows 2 - es wurde mit dem neuen, ordnungsgemäß gewarteten MSYS2 erstellt und verfügt außerdem über viele neue Funktionen, zahlreiche Fehlerkorrekturen, Sicherheitsverbesserungen usw. Wenn möglich, wird auch empfohlen, die 64-Bit-Version zu verwenden . Die Umgehungsumgehung für 32-Bit-Systeme wird jedoch automatisch hinter den Kulissen durchgeführt, sodass die Wahrscheinlichkeit, dass das Problem dort auftritt, ebenfalls geringer ist.
- Ein einfacher Neustart des Computers, um den Adressraum zu bereinigen (Laden dieser Module unter einer anderen zufälligen Adresse) könnte funktionieren, aber wirklich, aktualisieren Sie einfach auf Git für Windows 2, um die Sicherheitskorrekturen zu erhalten, wenn nichts anderes.
Hacky-Lösungen:
- Das Ändern
PATH
kann manchmal funktionieren, da es möglicherweise msys-1.0.dll
unterschiedliche Versionen von Git oder anderen MSYS-basierten Anwendungen gibt, die möglicherweise unterschiedliche Adressen, unterschiedliche Größen dieses Heaps usw. verwenden.
- Ein erneutes Basieren
msys-1.0.dll
kann Zeitverschwendung sein, da 1) eine DLL bereits Umzugsinformationen enthält und 2) "in jeder Version des Windows-Betriebssystems nicht garantiert werden kann, dass eine (...) DLL immer im selben Adressraum geladen wird". sowieso ( Quelle ). Dies kann nur helfen, wenn das msys-1.0.dll
selbst an der widersprüchlichen Adresse geladen wird, die es dann zu verwenden versucht. Anscheinend ist das manchmal der Fall, da dies die Git für Windows-Leute automatisch auf 32-Bit-Systemen tun .
- In Anbetracht der obigen Ergebnisse habe ich die
msys-1.0.dll
Binärdatei ursprünglich binär gepatcht , um einen anderen Wert für zu verwenden, _cygheap_start
und das Problem wurde sofort behoben.