Ich möchte das mit der wichtigen Anmerkung vortragen, dass ich kein C / C ++ - Programmierer bin und sehr wenig darüber weiß, wie die Verknüpfung von Bibliotheken in C. funktioniert / p>
Unser Code verwendet libstdc ++. so.6 (gcc 3.4, glaube ich). Wir haben vorkompilierte Bibliotheken (closed source) von Drittanbietern, die libstdc ++. So.5 verwenden (gcc 2. etwas oder 3.2, glaube ich). Dies ist auf Linux. Wir haben sowohl eine .a als auch eine .so Version der Third Party Lib.
Ist es möglich, unsere App mit den 3rd-Party-Bibliotheken zu erstellen? Wie? Ist es möglich, unsere App zu erstellen / zu betreiben, ohne libstdc ++ .so.5 installiert unsere unsere Maschinen, wie?
Wenn ich einige wichtige Informationen vergessen habe, lassen Sie es mich bitte wissen - ich weiß kaum, was mit diesem Zeug relevant ist. Ich weiß, dass eine vollständige Antwort wahrscheinlich nicht möglich sein wird; Ich suche wirklich nach Richtung und Führung. Statische Verknüpfung dies, dynamische, das, das vor, Build-so-und-so, wechseln Sie zu Version X, oder symbolisieren Sie die Quizdoodle, etc.
Aktualisierung:
Wir haben versucht, dlopen
mit RTLD_LOCAL
zu verwenden, um die 3rd-Party-Bibliothek vom Rest unserer App zu isolieren. Dies scheint meistens zu funktionieren, jedoch bleiben uns aus unbekannten Gründen große Speicherlecks. Wir vermuten, dass, wenn wir dlopen
aufrufen, die Third-Party-Bibliothek Symbole wie malloc
von der bereits geladenen .so.6 einliest und die Dinge durcheinander kommen.
Um zu lachen, haben wir versucht, die Bibliothek von Drittanbietern in LD_PRELOAD
zu setzen, dann haben wir unsere App ausgeführt, und die Speicherlecks scheinen vollständig zu verschwinden.
Sie können versuchen, eine Wrapper-Bibliothek um Ihre 3rd-Party-Bibliothek zu bauen: benutzen Sie die statische Version dieser Bibliothek + verbinden Sie sie mit der statischen Standard-Bibliothek (-static-libgcc - stellen Sie sicher, dass Sie eine korrekte Version über -L) . Es ist wichtig, diese Wrapper-Bibliothek ordnungsgemäß zu schließen, d. H. Nur Symbole aus der ursprünglichen Bibliothek von Drittanbietern sollten exportiert werden, alles andere sollte versteckt werden. Auf diese Weise wird die Wrapper-Bibliothek alle benötigten Symbole für Ihre Anwendung verfügbar machen und Standard-Inhalte einkapseln. Beachten Sie, dass es nicht funktioniert, besonders wenn einige Speicheroperationen zwischen Ihrem Code und dem Code von Drittanbietern geteilt werden (z. B. wenn Sie Speicher in Ihrem Code zuweisen und bei Drittanbietern freigeben) ... in diesem Fall kann die einzige Option sein, diesen dritten Platz zu behalten Party lib in einem anderen Prozessraum.
Ich denke nicht, dass die oben erwähnte dynamische Option funktionieren würde, weil Sie genau das gleiche Problem bekommen - nur später.
Im Allgemeinen ist es besser, keine Binaries mit unterschiedlichen Laufzeiten im selben Prozessraum zu mischen. Es ist fast immer ein Rezept für eine Katastrophe.
Fragen Sie Ihren Händler nach einer neueren Version der Bibliothek, die etwas verwendet, das nicht schrecklich veraltet ist. Andernfalls können Sie sehen, ob Ihre neue Anwendung immer noch mit der älteren Version der Bibliothek arbeitet und diese ggf. zurück portieren. Der Versuch, zwei verschiedene Versionen der gleichen Bibliothek zu haben, verlangt Schmerz und ich glaube nicht, dass Sie eine akzeptable Lösung finden.
Es ist zwar leicht, gleichzeitig libstdc ++. so.6 und libstdc ++. so.5 mit Ihrer Anwendung zu verknüpfen, aber sein Verhalten ist ziemlich undefiniert, weil die Symbole aus jeder Bibliothek zufällig stammen.
Der beste Weg zum Erfolg IMO ist es, eine eigene Anwendung um Ihre 3rd-Party-Lib auf einem alten System (das ein kompatibles gcc wie gcc 3.3 verwendet) zu erstellen und es über IPC mit Ihrer Hauptanwendung kommunizieren zu lassen ( zB Shared Memory). Auf diese Weise, nein
Wenn Sie libstdc ++. so.5 auf Ihrem Zielsystem nicht behalten wollen, dann ist das ganz einfach: Verwenden Sie gcc's -static Flag, um libstdc ++. a mit Ihrer Wrapper-Anwendung zu verknüpfen.
Während einer der bisherigen Ansätze funktionieren mag, ist es meiner Meinung nach sicherer zu sagen, dass Sie dies nicht direkt und zuverlässig tun können. Wenn Sie einen Wrapper mit vollständig C-basierten APIs schreiben (nur C-kompatible Strukturen, von malloc / free verwalteter Speicher usw.), können Sie möglicherweise die Lösung von pobedim verwenden. Wenn Sie jedoch C ++ - Strukturen austauschen müssen, ist dies nicht sicher, selbst wenn Sie die Verbindung herstellen könnten, würden verschiedene Standardbibliotheksimplementierungen für die gleichen Objekte verwendet werden. Außerdem ist die C ++ ABI möglicherweise nicht kompatibel zwischen .5- und .6-basierten Codebasen (ich kann mich nicht sicher erinnern, wie die hauptsächliche Änderung von Gnu C ++ ABI vor ein paar Jahren mit Standard-Bibliothekssonames zusammenhing).
>Ich denke, der sicherste Ansatz zur Lösung dieses Problems besteht in der Verwendung eines Multiprozess-Ansatzes mit einer Art IPC zwischen Ihrer Anwendung und einem Ressourcen- / Computer-Server-Prozess, der auf der betreffenden Bibliothek basiert. Sie können CORBA, D-Bus, Sun RPC oder ein Ad-hoc-Protokoll über Pipes oder Sockets verwenden, um diese Aufgabe zu erledigen. Ich habe dies bei der Verwendung von Closed-Source-32-Bit-Code in 64-Bit-Anwendungen getan, und es funktioniert gut genug. Sie werden einen Leistungseinbruch erleben, aber Sie werden auch die Probleme, die mit dem Mischen von C ++ Laufzeiten in einem Prozess verbunden sind, vollständig umgehen.