Build für mehrere Architekturen ?

lano

Mitglied
Moin.

wie kann ich auf einfache weise ein Programm für mehrere Architekturen bauen?

Als erstes würde mir crosscompiler einfallen.
Aber ich würde es bevorzugen dafür virtuelle maschinen zu benutzen.

Gibts da allgemeine Vorgehensweisen? Ideen ? Wie macht ihr das ?
 

Lowl3v3l

Mitglied
devCommunity-Experte
Uff. "Wie kann ich Matheaufgaben lösen?"^^

Crosscompiler sind eine Möglichkeit, die mal besser, mal schlechter, funktioniert. Interpreter(oder VMs wie die JavaVM) sind eine andere, oder Webanwendungen.

Alternativ kann man das natürlich in eine Virtuelle Maschine(qemu, Virtualbox) oder einen Container(docker, podman, jail...) klatschen.

Hängt natürlich davon ab wie verschieden die Architekturen sind, ggf. ists ne bessere Idee, das Programm zweimal zu schreiben(du kriegst keine Anwendung hin die gleichzeitig auf nem Mini-ARM und nem High-End-Supercomputer gut läuft).

Generell ist "Plattformunabhängigkeit" so ein bisschen ein falscher Freund, idR heißt das einfach nur, ein anderer Teil des Programms wird doppelt implementiert(also eigentlich ists nicht plattformunabhängig, der abhängige Teil ist nur die Arbeit von jemand anderem), oder dass man in Wahrheit nur für die Plattform "minimale Schnittmenge" programmiert, was natürlich auch oft nicht cool ist.

Was davon ein guter Weg ist hängt zu sehr vom Problem ab, um dazu was allgemeines sagen zu können.

mfg,
Lowl3v3l
 

german

Aktives Mitglied
devCommunity-Experte
@lano Du willst doch nicht etwa deinen C-POSIX-Mix auch für Windows kompilieren, oder? :D
 

aligator

Neues Mitglied
Also da dus ins allgemeine Forum gestellt hat, gehe ich mal von aus, das es dir nicht nur um C geht.

Dann wirds allerdings schwierig, wie @Lowl3v3l geschrieben hat hängt das von vielen Faktoren ab.
Jede Sprache hat unterschiedliche Möglichkeiten und zum Teil ist es auch wichtig, wie du Programmierst (z.B. unterstützt du Windows und Linux Dateipfade)
Script sprachen sind oft direkt portierbar, solange der Interpreter auf dem Zielsystem existiert.
Bei Bytecodesprachen wie Java geht in den meisten Fällen einfach, solange auf dem Zielsystem eine JVM existiert.
Bei Kompilierten sprachen wirds schwierig, weil dann oft Dinge je nach System unterschiedlich sein müssen.

Bei C ist es denke ich eher schwierig, es sei den man hat den Code gleich von Anfang an mit Crosskompatibilität im Hinterkopf geschrieben.
Anders wiederum ist Go: hier kann der Compiler von haus aus für alle unterstützten Systeme und Architekturen kompilieren und der compile muss dazu nicht auf dem zielsystem ausgeführt werden und die Standardbibliothek unterstützt auch alle Systeme. Also wenn man nicht grad C bindings verwendet hat man damit ähnliche Chancen wie mit einer Scriptsprache. (was, wie ich finde sehr Angenehm ist :))

Und ja bei C (zumindest beim GCC compiler) musst du für jede Zielarchitektur erst einen Crosscompiler compilieren, um für andere Architekturen als die aktuelle etwas zu Compilen.
Deshalb ist bei C tatsächlich eine Virtuelle Maschine auch eine sinnvolle möglichkeit, die ohne Crosscompiler aus kommt. Wobei das ganze bei größeren Projekten automatisiert werden kann.
 

aligator

Neues Mitglied
Naja zum automatisieren gibt es in größeren Projekten normal ne CI-Pipeline (für Tests, compiling, linting, etc...), und diese wiederum kann auch die verschiedenen Releases für die verschiedenen Ziele bauen. Zum ausführen der einzelnen Schritte können dan VMs erstellt werden (z.B. mit Hilfe von Kubernetes), oder für manche auch einfach Docker container verwendet werden, die dann die Befehle der Pipeline ausführen.
Das ist ein recht komplexes Thema, denn so ne Pipeline kann man auf unterschiedlichste Weis aufbauen.

Hat man so ne Pipeline, dann wird bei jedem Commit auf einen Branch versucht das Programm für alle Architekturen zu bauen.

Ab hier wirds dann allerdings für mich theoretisch, da ich sowas noch nicht selber aufgebaut hab (nur mal für ne JS Webanwendung, wo cross-compilen ja kein Thema ist.).

So ne Pipeline geht jetzt natürlich etwas weiter als deine Frage, aber evtl. findest du im Zusammenhang damit etwas, wie man (automatisiert) etwas für mehrere Systeme crosscompilen kann, ob nun durch die Pipeline oder manuelles ausführen eines scriptes.

Grundsätzlich wirst du bei C aber nicht um Crosscompiler und / oder VMs rum kommen. Zum automisieren wird dass dann halt im Prinzip in Scripte gepackt und ausgeführt.
 

aligator

Neues Mitglied
Ich hab grad das hier gefunden:
es gibt also bereits diverse Dockercontainer bei denen jeder einen Crosscompiler für ein bestimmtes System hat.
 

Lowl3v3l

Mitglied
devCommunity-Experte
Naja niemand sollte mehr freiwillig zum crosscompilen GCC benutzen, wenn er auch Open64 oder Clang benutzen kann um einfach direkt crosscompilen zu können. Bei Go stimmt das halt auch nur begrenzt(zum Beispiel crosscompiled es nur für ARMv5+, mit Darwin ARMv7+, Windows ARM funktioniert gar nicht, und nur für EABI-Kernel). Go ist auch nicht "plattformunabhängig", da steckt der abhängige Teil halt in irgendwelchen gigantischen Runtimes, und bei jedem etwas exotischeren Prozessor hast du verloren ;)

Wenn man etwas mit CI rumspielen will funktioniert, wenn man github benutzt, Travis recht super, ansonsten ist Teamcity von den IntelliJ-Leuten auch ganz cool. aber @aligator hat da schon recht, das vernünftig aufzusetzen ist selbst ne Wissenschaft und vmtl. Overkill. An sich halte iuch es aber, wenn man mehr Zeug anstellt für eine schlaue Idee , sowas einmal aufzusetzen, und dann einfach jedes neue Projekt einzuhängen und die Magie passieren zu lassen, da kann man ja auch gleich automatisiert testen, mit allen möglichen sanitizern, hat einfache rollbacks und kann deployen, wenn nötig. Kann ich nur empfehlen, wenn man gern bastelt geht da auch mit cron, incron, ein paar sanitizern, git, der Make-Implementierung deines Vertrauens(um Gottes Willen nicht GNU-Make, sondern ein BSD-Make oder Plan9-mk) und so wahnsinnig viel, es lohnt definitiv sowas mal aufzusetzen oder selbst zusammen zu hacken.

C für Anwendungsentwicklung ist halt insgesamt keine so geile Idee, wenn C++ irgendwie eine Option ist, einen der Gründe siehst du grad : die Standardlib auf die du dich irgendwie verlassen kannst ist minimalst, und es hat auch niemand sich je die Mühe gemacht, größere Abstraktionsframeworks(.NET, QT, Cocoa, Boost...) dafür zu schreiben, eben weil es keine so besonders schlaue Idee ist, schon auch weil extrem viele sinnvolle Abstraktionsmittel fehlen und das Tooling(fängt schon bei sinnvollen lintern an) eher... spartanisch ist.

Das heißt nicht dass C totaler Crap ist etc. Die Sache ist nur : C hat seinen Bereich, wie jedes Werkzeug, wo es gut ist. Und das entwickeln nichttrivialer Anwendungen in nicht radikal beschränkten Umgebungen gehört halt nicht dazu. C ist ein Makroassembler für Betriebsysteme und Microprozessoren. Man kann sicher auch mit nem Schraubenzieher ein Haus abreißen, aber ich nehm lieber ein paar Kilogramm TNT dafür.
 
Zuletzt bearbeitet:

aligator

Neues Mitglied
Go ist auch nicht "plattformunabhängig", da steckt der abhängige Teil halt in irgendwelchen gigantischen Runtimes, und bei jedem etwas exotischeren Prozessor hast du verloren
jo, klar, code-portabilität kommt immer mit anderen Einschränkungen in dem Fall mit großer Runtime und nur ausgewählte Ziele. Dafür muss man den Code nicht für jedes Ziel anpassen. Für die Architekturen und Prozessoren, die Go unterstützt funktioniert es gut.
Wirklich plattformunabhängig gibt es nicht, weil immer entweder ein Interpreter, compiler, vm oder sonst was vorhanden sein muss was das Zielsystem unterstützt.
 

lano

Mitglied
Das einfachste für mich scheint zu sein ich bastel mir da nen script für.
Irgend ne Steuerdatei was alles gebaut werden soll.
Dann den Source aufs NAS laden und von da aus können sich dann die vms den source laden und bauen.
Das ergebniss dann wieder aufs nas schieben und quasi fertig.

Dann könnte ich auf der Mashine auf der die vms laufen nen script laufen lassen was immer nach neuen jobs sucht und die benötigten vms startet..
In den vms könnte ich ja eigentlich auch gleich die debs bauen und ins apt-Repository schieben.
 

Lowl3v3l

Mitglied
devCommunity-Experte
Schau dir mal ccache und distcc an, beides willst du definitiv benutzen. Auch von nem Compiler mit sinnvollem zwischenformat(wie clang mit llvm bitcode) könntest du profitieren, das minimiert den doppelt zu compilierenden Teil.
 
Oben Unten