@an die C++ Hasen:
Wenn ich ne statische Bibliothek erstellen will,
was ist besser:
Alle Funktionen in einer Cpp Datei?
oder
Jede Funktion in eine separaten CPP Datei?,
um das eigendliche Client Programm möglichst klein
zu bekommen?
Das alle Deklarationen in die H. Datei gehören,
weiß ich. ;-O
Genauer:
Ich habe ne Bibliothek mit 100 Funktionen.
In meinem Client benötige ich aber nur eine davon.
Linkt der Linker jetzt diese Funktion aus der Objektdatei
oder kann er nur ganze Objektdateien in den Clienten einbinden?
Uff!!
Fragen über Fragen, hoffendlich versteht mich einer bei dem
Anliegen...
mfg
~Mercedes~ schrieb:> Alle Funktionen in einer Cpp Datei?> oder> Jede Funktion in eine separaten CPP Datei?,
Jede Funktion in einer separaten Datei.
Alternativ geht auch 1 Quelldatei, die dann mehrfach bedinge übersetzt
wird, z.B. mit -DMODUL1, -DMODUL2, ... und entsprechende Abschnitte der
Datei in #ifdef MODUL1 geklammert.
Je nach Build-Umgebung und Projektorganisation kann die eine oder andere
Variante besser wartbar sein.
Für privaten Gebrauch und mit GNU-Tools (GCC) geht auch 1 Datei mit
-ffunction-sections -fdata-sections und dann mit -Wl,--gc-sections
linken.
Davon ab können sich Unterschiede ergeben, wenn man nur 1 riesigen Klotz
compiliert wegen Inlining oder Cloning, bei fine-grained Modulen (also
mit #ifdef oder n Quellen) besteht dieses Problem nicht.
Oliver S. schrieb:> Mit link time optimization sollte das kein Problem sein.>> Oliver
Das war doch mal eine der ersten und wichtigsten Aufgaben des Linkers?
Damals, als es noch richtige Linker gab?
Johann L. schrieb:> Oliver S. schrieb:>> Mit link time optimization sollte das kein Problem sein.>> Nicht portierbar.
Man muss den Code nicht ändern um auf einem anderen Compiler LTO nicht
zu verwenden, der Code funktioniert auch ohne LTO. Also warum soll es
nicht portierbar sein?
Bernd K. schrieb:> Johann L. schrieb:>> Oliver S. schrieb:>>> Mit link time optimization sollte das kein Problem sein.>>>> Nicht portierbar.>> Man muss den Code nicht ändern um auf einem anderen Compiler LTO nicht> zu verwenden, der Code funktioniert auch ohne LTO. Also warum soll es> nicht portierbar sein?
Wenn kein LTO verwendet wird und LTO die (angebliche) Lösung für das
Problem darstellen soll, dann ist es eben keine Lösung mehr.
Außerdem enthalten Object-Files nur lto und keinen (normalen)
Object-Code (mehr), zumindest für GNU Tools. Wenn also inkompatibles
lto verwendet wird – zum Beispiel weil sich die lto-Spezifikation von
einer Compilerversion zur nächsten geändert hat, was durchaus mal der
Fall ist, dann ist es entweder keine Lösung (weil tote Funktionen
vorhanden sind), oder der Compiler meckert – und dann ist es auch lein
Lösung. Oder beides.
Dito mit -ffat-lto-objects.
Spielt natürlich nur eine Rolle wenn man die Libs ausliefert. Zumindest
in Standard-Libs wie libc.a will man definitiv keinen lto-Code.
Meinen Dank, an alle hilfswilligen!
Hey, da sind sich noch nicht eimal die
Hasen richtig einig? ;-O
Es geht dabei um CLANG, genauer CLANG unter
Windows, noch genauer um den C++ Builder von
Embarcadero.
Und um kleine Tools mit grafischer Oberfläche zu erstellen.
Nun ist ja die Oberfläche objektorientiert und absolut
ineinander verzahnt, was bedeutet, das wenn man den kleinsten
Fuzz instanziiert, den ganzen Brocken in die EXE gelinkt bekommt.
Und Firemonkey, mit dem man geil Verspieltes machen kann,
ist sogar noch größer. :-(
Das wird man nicht verhindern können.
Wenn ich aber jetzt ne Lib erstelle, möchte ich wenigstens
nur die benötigten Funktionen meiner Lib in der exe haben.
Was ist LTO genau und kann CLANG das auch?
mfg
~Mercedes~ schrieb:> Was ist LTO genau und kann CLANG das auch?
LTO steht für "link time optimization" und bewirkt genau das ;)
Der Compiler schreibt keine echten Objektfiles mehr, sondern legt in den
.o-Dateien einen compilerspezifischen Zwischencode ab. Das eigentliche
"fertig-compilieren" findet dann zur Link-Zeit statt.
Das wirkt sich (ungefähr) so aus, als ob Du alle Quellen in ein einziges
C/C++-File geschrieben hättest. Dadurch, dass der Compiler so praktisch
alle Quellen auf einmal zu sehen bekommt, kann er sehr viel besser
optimieren (weil er beispielsweise so erkennen kann, welcher Code gar
nicht benutzt wird oder wo sich inlining lohnt).
ja, clang kann das auch.
Gibt auch noch den Trick alle cpp-Dateien in eine einzelne compilation
unit zusammenzupasten, per Perl-Skript oder auch per #include. Sprich,
du hast ganz normal organisierte Dateien, und dann nochmal eine die alle
cpp-Dateien #included und nur die kompilierst du.
So oder so:
1) Organisiere deine Dateien übersichtlich
2) Probiere mit Compiler/Linker-Flags das zu erreichen was du willst
3) Wenn und nur wenn das Ergebnis nicht gut genug ist, bau irgendwas in
das Build-System ein was es besser macht.
Nicht den Code unlesbar machen um fragwürdige Optimierungen zu erzielen,
das ist fast immer ein Fehler.
Markus F. schrieb:> ja, clang kann das auch.
Clang/LLVM hat damit sogar angefangen...
Johann L. schrieb:> Nicht portierbar.
Ist kompilierter C++ Code sowieso kaum. Wenn man sich über Portabilität
Gedanken macht, muss man sowieso prüfen zu welchen Toolchains es
kompatibel sein soll und ob LTO hier konkret ein Hindernis ist.
Du entwickelst eine GUI Applikation und machst dir Gedanken über die
Größe von 100 Funktionen? Darf ich Fragen wie groß die .exe eines
Minimalbeispiels (Fenster mit X-Button) bei dem genutzten Framework ist?
~Mercedes~ . schrieb:> Ne schön bunte "Hallo Board" Anwendung braucht> ungepackt rund 3 Mb, gepackt mit Winrar knapp 800 Kb.>> Statisches Linken, Optimierung -o3
Jo ok, das ist dann wirklich eine völlig sinnlose premature optimization
was du hier erfragst ;)
Vergiss es einfach und mach's irgendwie.
Wilhelm M. schrieb:> Was spricht gegen header-only?
- Lange compile-Zeiten
- Trashing von Namespaces mit nur für die Implementierung der Funktion
relevanten Symbolen
- generell häufigere Rekompilierung durch für die Schnittstelle der
Funktionen eigentlich völlig irrelevante Änderungen
- häufige Vermischung von Informationen, die ein Benutzer der
Schnittstelle benötigt, mit völlig uninteressanten Details der
Implementierung.
Für große Projekte daher vollkommen ungeeignet. Daraus folgend:
- schlechte Skalierbarkeit
~Mercedes~ . schrieb:> Ne schön bunte "Hallo Board" Anwendung braucht> ungepackt rund 3 Mb, gepackt mit Winrar knapp 800 Kb.
Das ist doch heutzutage vollkommen OK.
3MB in nem statisch gelinkten Binary das man überall einfach so ohne
Installation laufen lassen kann ohne jegliche DLL-Hell sind mir allemal
lieber als jedesmal separat noch dafür sorgen daß das benötigte
GUI-Toolkit oder anderer Kram installiert ist oder einen Berg von DLLs
mitliefern die dann insgesamt 30MB statt 3MB groß sind, vor allem auf
Windows wo es keinen Paketmanager gibt der einem diesen Streß abnimmt.
3MB hätte mich vielleicht gestört in der Zeit als man noch mit
1.44MB-Disketten unterwegs war, heute sind 3MB als vergleichsweise klein
zu betrachten! Lass es einfach so, die Nutzer werden sich nicht
beschweren, ganz im Gegenteil, die werden sich verwundert die Augen
reiben daß diese ganze aufwendige Software nur aus dieser einen winzigen
Datei besteht, sie werden Dich lobpreisen für diese Meisterleitung und
andere die für vergleichbar komplexe Software nen 800MB Installer
ausliefern ermahnen sich mal ein Beispiel an Dir zu nehmen!
Huch?!?!
Bernd meinte:
> Das ist doch heutzutage vollkommen OK.
Aber der stumm schweigende Andreas wird mich
nicht loben, sondern skalpieren, wenn ich sein
Board vollmülle! ;-O ;-D
An mir ein Beispiel nehmen? Ich sehe zur Zeit
wie ne "Rechte Tussi" aus, mit meiner Glatze
mit Hieroglyphen drauf. :-O ;--((
Nö. Ich brauche noch Zeit, bis ich ein Beispiel bin.
Was haltet ihr von Exepackern?
Son Teil, was die EXE beim Starten automatisch entpackt?
Oder das man die Ressurcen komprimiert in der
Exe hält, etwa durch ein Single Dateisystem?
mfg
~Mercedes~ schrieb:> Was haltet ihr von Exepackern?> Son Teil, was die EXE beim Starten automatisch entpackt?
Kann man machen, ein bekannter Packer ist UPX. Bei gepackten EXE kann es
bei Antivirenprogrammen schon mal zu Fehlalarmen kommen.
~Mercedes~ schrieb:> Was haltet ihr von Exepackern?> Son Teil, was die EXE beim Starten automatisch entpackt?
Braucht mehr Speicher weil alles ins RAM entpackt und dort gehalten
werden muss anstatt einfach nur die gerade benötigten Teile zu mappen.
Und es ist vollkommen unnötig weil Dein C++-Builder oder Delphi bereits
erstaunlich kleine Exe macht. Die von Lazarus sind sogar noch nen Tick
größer, aber selbst die sind noch um Faktor 10 unter jeglicher denkbarer
Schmerzgrenze.
Also vergiss den Blödsinn einfach und kümmer Dich stattdessen um das
eigentliche Programmierproblem anstatt Zeit mit der Prokrastination über
derartigem nutzlosen Unsinn zu vergeuden. Du könntest schon halb fertig
sein, also mach hin!
Bernd K. schrieb:> ~Mercedes~ schrieb:>> Was haltet ihr von Exepackern?>> Son Teil, was die EXE beim Starten automatisch entpackt?>> Braucht mehr Speicher weil alles ins RAM entpackt und dort gehalten> werden muss anstatt einfach nur die gerade benötigten Teile zu mappen.
Gilt das auch für DLL'S? Werden die auch vollständig geladen?
> Und es ist vollkommen unnötig weil Dein C++-Builder oder Delphi bereits> erstaunlich kleine Exe macht. Die von Lazarus sind sogar noch nen Tick> größer, aber selbst die sind noch um Faktor 10 unter jeglicher denkbarer> Schmerzgrenze.
Wirklich? Wenn Du es sagst... :-O
> Also vergiss den Blödsinn einfach und kümmer Dich stattdessen um das> eigentliche Programmierproblem anstatt Zeit mit der Prokrastination über> derartigem nutzlosen Unsinn zu vergeuden. Du könntest schon halb fertig> sein, also mach hin!
Erst muß ich meine OP überstehen... ;---O
Ich danke allen Beteiligten des Threads für Eure Hilfe!
mfg