Hi,
ich habe mal eine Frage zu dem Orginaldateinamen bei Apps die mit Visual
Studio 2022 erstellt werden.
Wenn ich eine Programm erstelle, z.B. Hallo Welt oder so und hinterher
nicht mehrere Dateien haben will sondern eine einzelne exe Datei, kann
ich das ja mit der Veröffentlichen Funktion machen.
Also Bereitstellungsmodus Frameworkabhängig, Zielruntime win-x64 und
Einzelne Datei erstellen.
Das alles klappt auch soweit nur steht dann bei der exe die rauskommt
beim Orginaldateinamen unter Details nicht Hallo Welt.exe sondern Hallo
Welt.dll. Ich finde das etwas unschön und hätte in dem Feld gerne den
Namen mit der Endung .exe stehen, wie bekomme ich das hin?
Programmierer schrieb:> Das alles klappt auch soweit nur steht dann bei der exe die rauskommt> beim Orginaldateinamen unter Details nicht Hallo Welt.exe sondern Hallo> Welt.dll.
Das bedeutet, daß Deine Projekteinstellungen keine ausführbare Datei
erzeugen, sondern eben eine DLL.
Projekt neu anlegen, und diesmal richtig durch den Wizard durchklicken.
DerEgon schrieb:> Programmierer schrieb:>> Das alles klappt auch soweit nur steht dann bei der exe die rauskommt>> beim Orginaldateinamen unter Details nicht Hallo Welt.exe sondern Hallo>> Welt.dll.>> Das bedeutet, daß Deine Projekteinstellungen keine ausführbare Datei> erzeugen, sondern eben eine DLL.>> Projekt neu anlegen, und diesmal richtig durch den Wizard durchklicken.
Also dann nochmal in langsam: Es wird beim normalen Kompilierungsvorgang
eine EXE erstellt, nein es wurde nicht fehlerhafterweise eine DLL
erstellt. Visual Studio 2022 geht aber trotzdem anscheinend jetzt immer
hin und verlagert die eigentliche Funktionalität in eine DLL die von
dieser Exe aufgerufen wird. Da ich es aber für kleine Tools unpassend
finde den ganzen Raffel zu verschicken, will ich alles in die Exe
packen, unter anderem dafür gibts die Möglichkeit beim Veröffentlichen
alles in eine Exe zu packen, was auch problemlos funktioniert und wie
erwartet läuft. Nur ist in den Details der Exe eben der Originalname mit
Endung DLL.
Ansonsten wäre es schön wenn nur Leute antworten würden die zumindest
halbwegs eine Ahnung haben und nicht nur heiße Luft von sich geben.
Da es offensichtlich bei manchen mit dem Textverständnis und/oder Wissen
hapert, hier nochmal als Bilderbuch:
1 - Der Ausgabetyp: Konsolenanwendung, nix Klassenbibliothek.
2 - Was beim Kompilieren rauskommt, 1 EXE, 1 DLL, 1 PDB und 2 JSON.
3 - Und schon an diesem Punkt steht in der EXE als Originaldateiname
Hallo Welt.DLL
4 - Wenn ich jetzt das Ganze veröffentliche als einzelne EXE
5 - Die einzelne EXE in die die DLL integriert wurde, jetzt 150 kB.
6 - Die Details der einzelnen EXE, wieder Originalname Hallo Welt.DLL
Kenne mich mit dem .net nicht wirklich aus. Eventuell eine definierte
Zielplattform/ runtimr festlegen; sonst wird u.U. ein Universal Binary
gebacken (als DLL) und das via einem Stup (exe) gestartet.
Du hast einen Denk-Fehler.
Wenn du eine Exe eingestellt hast, wird auch NUR eine EXE erstellt, ALS
PROGRAMM. Hier HELLO-WORLD.EXE.
Der Rest des Geraffel dort ist das gemiste was der "Hobby-Installer"
braucht.
Wenn du keine "Zubehör-Dateien" (wie Datenbanken etc.) brauchst kannst
du die EXE aus den RELASE-Ordner nehmen und i.d.R. weiter versenden,
verteilen etc. Kannst du gern testen. Datei (die Exe) auf ein Stick
kopieren und an anderen Rechner (VM) starten. Ist das Framework drauf,
läuft die Software einwandfrei.
Bei EXTERNEN DLL müssen die natürlich im Paket sein, und auch
registriert. Genau so wie Datenbanken die die Exe haben will. Aber das
ist dann schon installieren für Fortgeschrittene. ;) Wo bei , genau
DAFÜR ist das Geraffel gut. Ansonsten steht da nix gescheites drin. Für
den Installations-Creator sind da halt die Infos drin, das er NIX
zusätzlichen kopieren muss. Aber VORSICHT, das Spielzeug vergisst gerne
was, das muss man ihm dann extra sagen. Datenbanken z.b.
MS geht inzwischen davon aus das die Framework o. Runtime-Dateien sich
auf Zielrechner befinden.
Das da, ist nix anderes als eine Hilfe für ein Installer der billigsten
Sorte, bzw. Anweisungen für ihn.
So was ähnliches gab es schon bei VB 3.1. ;) Da war das Endergebnis eine
SETUP.EXE und ein paar Hilfs-Dateien.
Ich weiß zwar nicht wo unter VS es aktuell ist, aber irgendwo gibt es
eine Funktion für die Erstellung eines Installers. Der will das ganze
Geraffel haben, und macht dann die Installations-Datei.
Ich persönlich habe mir den KOSTENPLFICHTIGEN Advance-Installer besorgt.
Den würde ich in deinen Beispiel nur sagen wo die "Hello-Word.exe" ist,
und den Rest macht er selbst.
Der macht eine RICHTIGE Installationsdatei. Mit jede Menge Optionen wie
z.b. Backup der alten Dateien, Dateimanagment (Sehr wichtig bei
Datenbanken die die Software NICHT selbst anlegt) u.w.mehr.
Schlaumaier schrieb:> Du hast einen Denk-Fehler.
Womit du dich eigentlich auskennen müsstest, aber nichtmal das
funktioniert bei dir vernünftig.
> Wenn du eine Exe eingestellt hast, wird auch NUR eine EXE erstellt, ALS> PROGRAMM. Hier HELLO-WORLD.EXE.
Unsinn, seit einiger Zeit kompiliert Visual Studio nur noch in dlls und
die exe ist lediglich der Wrapper dafür.
> Der Rest des Geraffel dort ist das gemiste was der "Hobby-Installer"> braucht.
Unsinn, es gibt da keinen Installer.
> Wenn du keine "Zubehör-Dateien" (wie Datenbanken etc.) brauchst kannst> du die EXE aus den RELASE-Ordner nehmen und i.d.R. weiter versenden,> verteilen etc. Kannst du gern testen. Datei (die Exe) auf ein Stick> kopieren und an anderen Rechner (VM) starten. Ist das Framework drauf,> läuft die Software einwandfrei.
Da die exe der Wrapper für die dll ist, geht das natürlich nicht. Was du
meinst ist die Abhängigkeit vom .net Framework, den man
Bereitstellungsmodus (Bild 4 des TO) regeln kann, hat aber mit der
Wrapper Nummer so garnix zu tun.
> Bei EXTERNEN DLL müssen die natürlich im Paket sein, und auch> registriert. Genau so wie Datenbanken die die Exe haben will. Aber das> ist dann schon installieren für Fortgeschrittene. ;) Wo bei , genau> DAFÜR ist das Geraffel gut. Ansonsten steht da nix gescheites drin. Für> den Installations-Creator sind da halt die Infos drin, das er NIX> zusätzlichen kopieren muss. Aber VORSICHT, das Spielzeug vergisst gerne> was, das muss man ihm dann extra sagen. Datenbanken z.b.
ES GIBT DA KEINEN INSTALLER, RAFF ES DOCH!
> MS geht inzwischen davon aus das die Framework o. Runtime-Dateien sich> auf Zielrechner befinden.
Und wenn man den Bereitstellungsmodus auf Unabhängig stellt, muss das
Framework nicht auf dem Zielrechner sein, es wird dann eben nur groß.
> Das da, ist nix anderes als eine Hilfe für ein Installer der billigsten> Sorte, bzw. Anweisungen für ihn.
Unsinn, das ist kein Installer, immer noch nicht.
> So was ähnliches gab es schon bei VB 3.1. ;) Da war das Endergebnis eine> SETUP.EXE und ein paar Hilfs-Dateien.
Wieder am Thema vorbei.
> Ich weiß zwar nicht wo unter VS es aktuell ist, aber irgendwo gibt es> eine Funktion für die Erstellung eines Installers. Der will das ganze> Geraffel haben, und macht dann die Installations-Datei.
Und schon wieder der Installer um den es nicht geht.
> Ich persönlich habe mir den KOSTENPLFICHTIGEN Advance-Installer besorgt.
Dumm genug bist du dafür, ja.
> Den würde ich in deinen Beispiel nur sagen wo die "Hello-Word.exe" ist,> und den Rest macht er selbst.
Du hast keine Ahnung.
> Der macht eine RICHTIGE Installationsdatei. Mit jede Menge Optionen wie> z.b. Backup der alten Dateien, Dateimanagment (Sehr wichtig bei> Datenbanken die die Software NICHT selbst anlegt) u.w.mehr.
Und wieder am Thema Vorbei.
Übst du das eigentlich oder kannst du einfach so komplett daneben
liegen?
potentielle Handlungsmöglichkeiten:
- .rc File anschauen
- .manifest anschauen
- CMake nutzen
- Abhängigkeiten in der Projektmappe ausmisten
- sich mal die Ausgabe-Variablen in den Projekteinstellungen anschauen
- das feine Manual lesen auf MSDN
- ...
Programmierer schrieb:> Der Ausgabetyp: Konsolenanwendung, nix Klassenbibliothek.
In .NET wird alles über Klassen gemacht auch eine simple
Konsolenanwendung.
Programmierer schrieb:> 2 - Was beim Kompilieren rauskommt, 1 EXE, 1 DLL, 1 PDB und 2 JSON.
Ja das ist bei .NET-Gedöns so. Das eigentliche Programm ist in diesen
DLL's drin. Die EXE ist nur ein Vehikel um die DLL('s) am Ende
ausführen.
Am Ende mußt Du noch viel mehr mit Deinem Programm ausliefern als Du
denkst. Wenn Du in Deinem "Hallo Welt" auch nur eine einzige Klasse aus
.NET6.0 verwendest, mußt Du als Programmentwickler dafür sorgen das auf
dem Zielsystem das .NET6.0 Framework installiert ist bzw. während der
Installation mit installiert wird, damit Dein Programm dann auch auf dem
Zielsystem ausführbar ist.
Wenn Du wirklich nur eine reine (native) EXE witergeben willst, dann
mußt Du Dir eine andere Programmiersprache/-umgebung suchen, die aus
Deinem Quelltext eine native EXE erzeugt.
PittyJ schrieb:> Zuerst den Nicknamen von Programmierer auf DAU ändern. Ansonsten ist das> eine Beleidigung.
Die Formulierung von dem Pitty ist zwar nicht sehr nett, aber er hat
nicht ganz unrecht, denn Du mußt noch viel lernen und von einem
richtigen Programmierer bist Du noch weit entfernt.
Schlaumaier schrieb:> Wenn du eine Exe eingestellt hast, wird auch NUR eine EXE erstellt, ALS> PROGRAMM. Hier HELLO-WORLD.EXE.
Du hast eben wieder mal so gar keine Ahnung. Bei .NET wird alles in
DLL's verpackt die EXE ist nur ein Hilfsmittel um den Kram am Ende als
App erscheinen zu lassen.
Dein Folgeposter, der Tim, hat das korrekt erkannt, wenn er schreibt:
Tim T. schrieb:> Unsinn, seit einiger Zeit kompiliert Visual Studio nur noch in dlls und> die exe ist lediglich der Wrapper dafür.
Zeno schrieb:> Programmierer schrieb:>> Der Ausgabetyp: Konsolenanwendung, nix Klassenbibliothek.> In .NET wird alles über Klassen gemacht auch eine simple> Konsolenanwendung.
Nur dass für eine Klassenbibliothek kein exe Wrapper erzeugt wird und
diese sich auch nicht als einzelne exe Datei, eventuell sogar
"Frameworkunabhängig" veröffentlichen lassen.
> Programmierer schrieb:>> 2 - Was beim Kompilieren rauskommt, 1 EXE, 1 DLL, 1 PDB und 2 JSON.> Ja das ist bei .NET-Gedöns so. Das eigentliche Programm ist in diesen> DLL's drin. Die EXE ist nur ein Vehikel um die DLL('s) am Ende> ausführen.
Ich denke das hat der TO durchaus verstanden, seine Frage war
offensichtlich eine andere. Es geht ihm nur darum dass das entsprechende
Feld in den Details der Datei anders ausgefüllt wird, weil die anderen
Schritte zum erzeugen einer Frameworkabhängigen einzelnen exe Datei hat
er ja schon richtig beschrieben.
> Am Ende mußt Du noch viel mehr mit Deinem Programm ausliefern als Du> denkst. Wenn Du in Deinem "Hallo Welt" auch nur eine einzige Klasse aus> .NET6.0 verwendest, mußt Du als Programmentwickler dafür sorgen das auf> dem Zielsystem das .NET6.0 Framework installiert ist bzw. während der> Installation mit installiert wird, damit Dein Programm dann auch auf dem> Zielsystem ausführbar ist.
Jein, entweder muss das Framework installiert sein oder alles was man
aus dem Framework benutzt muss mit im Verzeichnis liegen oder es muss
alles was man vom Framework benutzt in der exe eingebunden sein.
> Wenn Du wirklich nur eine reine (native) EXE witergeben willst, dann> mußt Du Dir eine andere Programmiersprache/-umgebung suchen, die aus> Deinem Quelltext eine native EXE erzeugt.
Natürlich kann man eine "native" exe weitergeben, da drin ist dann ein
nativer Loader für die ebenfalls in der exe fest eingebundenen dlls.
> PittyJ schrieb:>> Zuerst den Nicknamen von Programmierer auf DAU ändern. Ansonsten ist das>> eine Beleidigung.> Die Formulierung von dem Pitty ist zwar nicht sehr nett, aber er hat> nicht ganz unrecht, denn Du mußt noch viel lernen und von einem> richtigen Programmierer bist Du noch weit entfernt.
Ich halte die Frage des TO für mehr als gerechtfertigt, oder welcher
Grund fällt dir ein warum im Originaldateiname-Feld in der exe unbedingt
der Name der dll stehen sollte? Und ich muss gestehen, dass mir außer
der Einsatz von Drittanbieter Tools keine Möglichkeit dafür bekannt ist,
was aber wiederum Probleme beim Signieren erzeugen könnte...
Schlaumaier schrieb:> Tim T. schrieb:>> Unsinn, es gibt da keinen Installer.>> https://docs.microsoft.com/de-de/visualstudio/deployment/installer-projects-net-core?view=vs-2022>> Nur für den Fall das du den mal brauchst.>> Tim T. schrieb:>> Unsinn, das ist kein Installer, immer noch nicht.>> Doch er ist da. ;) MS schwindelt nicht immer. ;)
Gott scheiß Hirn vom Himmel, natürlich existiert in VS die Möglichkeit
den Installer mit seinem Projekt zu nutzen, aber das hat GARNIX mit der
Fragestellung oder dem restlichen Geschreibsel von dir zu tun.
> Tim T. schrieb:>> Und wieder am Thema Vorbei.>> Mag ja sein, aber von dir ist auch keine Sinnvolle Antwort.
Weil ich für die eigentliche Frage des TO auch keine wirklich
befriedigende Antwort habe. Für dich: Es ging offensichtlich nur um den
Eintrag im Originaldateinamen-Feld der veröffentlichten exe. Und anstatt
das du einfach mal die Finger still hälst, weil du wirklich nach allen
Maßstäben keinerlei Ahnung hast, schwafelst du wieder eine Grütze
zusammen die dem TO im besten Fall nicht hilft und in allen anderen
Fällen Lebenszeit für die Verfolgung eines komplett blödsinnigen
Ansatzes kostet.
Tim T. schrieb:> Jein, entweder muss das Framework installiert sein oder alles was man> aus dem Framework benutzt muss mit im Verzeichnis liegen oder es muss> alles was man vom Framework benutzt in der exe eingebunden sein.
Ich kenne es so, daß das Framework passend installiert sein muß. Ich
habe mal eine Weile an einem etwas umfangreicheren .NET-Projekt mit
gearbeitet und da haben wir beim Installieren der Anwendung geprüft, ob
das passende Framework auf dem System installiert ist. Wenn nicht wurde
das Framework installiert und zwar nach den Vorgaben von MS, also nicht
im Programmverzeichnis. Bei uns wurde das Framework einfach mit ins
Setup eingepackt und bei Bedarf installiert.
Die Applikation selbst war nie eine einzelne EXE und ich wüßte auch
nicht wo ich das in VS einstellen sollte, muß allerdings dazu sagen, daß
ich die letzten 2 Jahre nichts mehr mit .NET gemacht habe. Ich habe da
gerade mal nachgeschaut, lt. MS
(https://docs.microsoft.com/de-de/dotnet/core/deploying/single-file/overview?tabs=cli)
muß ich dazu in der Projektdatei einen speziellen Eintrag machen damit
das alles in eine EXE gepackt wird. Ich würde das so interpretieren, das
da von VS aus keine Option vorgesehen ist.
Eine Echte EXE ist das aber auch nicht, eher eine Art Archiv, denn der
Inhalt wird erst in ein Verzeichnis entpackt und dann erst ausgeführt.
Zitatat aus dem verlinkten Beitrag:"... wenn ein Benutzer Ihre einzelne
Datei-App ausführt, extrahiert .NET Core-Host zuerst alle Dateien in ein
Verzeichnis, bevor die Anwendung ausgeführt wird.". Zumindest bist
.NET3.0 war das so. Ab 5.0 wir es lt. MS direkt ausgeführt - vermutlich
nur in den Speicher entpackt. Eine echte native EXE ist das in meinen
Augen nicht. Die resultierende EXE ist wohl eher ein Container für die
App.
Ich denke, das ist durch das Betriebssystem bedingt, also
durch Windows. Das zeigt in den Details auch die Abhängigkeiten
an. Anbei mal ein Bild von einer anderen Sprache, die ein Interpreter
ist und die Runtime Prfrun32.exe in die Original-Exe mit einbindet.
Also beim Compilieren zu einer eigenständigen .Exe.
Dort wird ja auch die Prfrun32.exe vom compilierten Bytecode beim
Start aufgerufen.
Also ich habe es jetzt mal getestet, mit dem .NET 4.72 und 4.8 Framework
wird keine DLL erstellt und ich kann dann einfach die EXE aus dem
Release Ordner nehmen. In der Datei stimmt dann auch der
Orginaldateiname.
Es ist also nicht wie von mir zuerst vermutet von der Version des
VisualStudios abhängig sondern von der Version des verwendeten .NET
Frameworks.
Aber gibt es jetzt eine Möglichkeit das Feld auch bei Verwendung von
.NET 6 irgendwie zu ändern?
Ok, ich habe jetzt rausgefunden das der Name im Feld Orginaldateiname
immer der Assembyname ist. Allerdings wird wohl immer .dll angehangen
egal ob man schon eine Endung vorgibt oder nicht.
Da gibt es wohl immer bessere Möglichkeiten, die Abhängigkeiten
zu verstecken. Wenn ich nun ein PureBasic - Programm nehme, sieht
man keine Abhängigkeiten mehr. Das ist eine native .exe. Der
PB-Compiler generiert reinen Assembler-Output und schickt diesen
durch den freien, kostenlosen mitgelieferten FASM. Der produziert
dann eine reine native .exe.
Es war ja in der Vergangenheit (Anfang Windowszeitalter und vor .Net)
so, daß man bei VisualBasic die VBRUNXX.dll (XX = Versionsnummer)
mitgeben
mußte. Wenn man diese ins Systemverzeichnis kopierte, konnten alle
Anwendungen, die mit der richtigen Version von VB erstellt wurden,
aufgerufen werden. Das war damals auch bedingt durch den knappen und
auch teuren Arbeitsspeicher. Jeder weiß, daß man eine DLL bei
Progrmmstart laden und bei Programmende entladen kann. Damit hatte
man beim Aufruf mehrerer VB-exen einen viel kleineren Speicherbedarf
(Multitasking).
Heutzutage wird der Spieß oft einfach umgedreht : Die Runtime startet
(bei VB-Net läuft sie vielleicht schon beim Windowsstart ?) und ruft
das vor-compilierte Programm auf.
So ähnlich ist es auch bei meinen Profan-Programmen.
Die könnte ich auch per Kommandozeile aufrufen :
die Quellcodedatei -> Profan.exe quellcodedatei.prf
die vorcompilierte Bytecodedatei (.prc) -> prfrun32.exe
bytecodedatei.prc
Sowhol der Interpreter (Profan.exe), als auch die Runtime (Prfrun32.exe)
sind quasi Interpreter. Wenn es da ein Update gibt, bekommt man immer
beide zugeschickt bzw. kann es downloaden.
Das ist mal meine Interpretation des ganzen.
Heinz B. schrieb:> Das ist eine native .exe. Der> PB-Compiler generiert reinen Assembler-Output und schickt diesen> durch den freien, kostenlosen mitgelieferten FASM. Der produziert> dann eine reine native .exe.
Das kann man eigentlich mit jeder Programmiersprache so machen, wenn man
den passenden Compiler hat. Das ging sogar mit dem bekannten QBasic.
QBasic-Programme wurden ja via QBASIC.EXE also dem Interpreter
gestartet. Es gab allerdings auch einen Compiler der aus dem
Basicprogramm eine richtige Exe gebaut hat.
Bei dem von Dir angeführten Profan, was ja eine basicähnliche Sprache
ist, ist es ähnlich.
Java und C# arbeiten mit vorcompiliertem Bytecote, der dann vom JIT
Compiler erst zur Laufzeit in ein lauffähiges Programm übersetzt wird.
Das hat Vor- aber auch Nachtteile. Vorteil ist das das Programm
prinzipiell plattformunabhängig ist, solange man keine spezillen OS
Funktionen nutzt. Man braucht außer dem vorkompilierten Bytecode halt
einen passenden JIT Compiler mit Runttimeumgebung.
PS: Wie man das mit C# in eine einzige EXE bekommt hatte ich hier
Beitrag "Re: Orginaldateiname Visual Studio 2022 App" kurz
angerissen. Scheint den TO aber nicht zu interessieren.
Da gab es sogar eine QBasic.Lib, die man mit dem freien
MS-DOS Linker per Batchdatei einbinden konnte.
Libs gibt es ja heute noch. Damit meine ich nicht die
Definitionsdateien im Klartext, sondern die Funktionen,
die in Maschinencode in den Libs gebunden sind. Wenn man etwas
tiefer in die Materie einsteigt, weiß man dann auch den kleinen
Unterschied zwischen so einer .Lib und einer DLL. Im Grunde sind
die eigentlich identisch.
Bei einer .Lib wird der Maschinencode der Funktionen beim Erstellen
der .exe direkt vom Linker eingebunden und die Referenzen aufgelöst.
Die Funktionsadressen werden dabei schon fest in die .exe verdrahtet.
Eine DLL wird erst zur Laufzeit eingebunden. Dabei sind die
Funktionen der DLL in einem Pool fest verdrahtet und können
erst nach dem Laden der DLL aufgerufen werden. Wenn man mal so
eine DLL genauer mit einem Tool anschaut, wird man feststellen,
daß das Instanzhandle der DLL und die Funktionsadressen der Funktionen
bei jedem Laden der DLL identisch sind. Die verhält sich quasi
wie eine .exe, die an eine feste Adresse im Arbeitsspeicher geladen
wird. Da mein Profan solche Funktionalität für DLLs besitzt (ImportDLL
und ImportFunc), hatte ich das schon öfter ausprobiert.
Bei JAVA sind das auch oft die .Jar Dateien und die zugehörigen
Defintionsdateien im XML-Format.
Heinz B. schrieb:> Eine DLL wird erst zur Laufzeit eingebunden. Dabei sind die> Funktionen der DLL in einem Pool fest verdrahtet und können> erst nach dem Laden der DLL aufgerufen werden.
Nein das stimmt so nicht ganz.
Ich kann eine DLL statisch oder dynamisch einbinden. Im ersteren Fall
muß die DLL vorhanden sein und die Funktionen die vom Programm
aufgerufen werden müssen in der DLL vorhanden sein, ansonsten kann das
Programm nicht starten.
Bei einer dynamisch geladenen DLL kann ich den Zeitpunkt des Einbindens
selbst bestimmen. Dazu prüft man zuerst ob die DLL als Datei vorhanden
ist. Danach wird diese geladen, wobei man ein Handle auf diese DLL
bekommt, über das man dann die Funktionen DLL aufrufen kann. Und auch
hier kann man zuvor prüfen ob die gewünschten Funktionen überhaupt
vorhanden sind. Das dynamische Einbinden der DLL hat halt den Vorteil,
das man das Programm auch bei nicht vorhandener DLL trotzdem benutzen
kann. Es stehen dann halt die durch die DLL bereitgestellten Funktionen
nicht zur Verfügung, was man aber programmtechnisch einfach abfangen
kann.
Beides ist dynamisches Einbinden, der Unterschied liegt nur darin, wer
das Einbinden vornimmt.
Was Du "statisch" nennst, ist statisches Linken mit der zur DLL
gehörenden Importlibrary. Das sorgt dafür, daß im Exe-Header (bzw. einer
Tabelle dort) stehende Referenzen auf DLLs vom Programmlader aufgelöst
werden, bevor das Programm gestartet werden kann.
Das erzeugt die allseits bekannten Fehlermeldungen à la "DLL xy nicht
gefunden" oder "Prozedureinsprungspunkt yz in DLL xy nicht gefunden".
Ob man die DLL beim Programmstart oder erst dann, wenn man die
Funktionen braucht, einbindet ist doch wohl egal. Da gibt es
vom Prinzip her keinen Unterschied. Die DLL muß in beiden Fällen
ja vorhanden sein. Das Programm kackt ja erst ab, wenn die entsprechende
Funktion der DLL aufgerufen wird.
Und ob das nun sinnvoll ist :
>Das dynamische Einbinden der DLL hat halt den Vorteil,>das man das Programm auch bei nicht vorhandener DLL trotzdem benutzen>kann. Es stehen dann halt die durch die DLL bereitgestellten Funktionen>nicht zur Verfügung, was man aber programmtechnisch einfach abfangen>kann.
Entweder schreibe ich mein Programm so, daß ich die Funktionen
selber programmiere und die DLL gar nicht erst brauche oder ich
nutze halt die Funktionen einer DLL. Wenn, dann sollte man erst
abfragen, ob die DLL da ist und geladen werden kann. Das ist das
gleiche, wie bei einer Datendatei, die ein Programm benötigt.
Da frage ich auch zuerst ab, ob die Datei existiert und handle
dementsprechend. Das nennt man guten Programmierstil und hat nichts
mit statisch und dynamisch zu tun.
Statisch kann man eine .Lib oder .obj einbinden, dynamisch eine
DLL. Daran sehe ich, daß du den Unterschied zwischen .lib und
DLL nicht kennst.
Wenn man das ganz gut mit der DLL machen will, bindet man diese
schon vorher als Ressource in die .exe und schreibt sie bei
Programmstart, bzw. Abfrage, ob sie da ist, in den Startordner,
wo auch die .exe liegt oder ins Systemverzeichnis.
Die Erfahrung habe ich mehrmals bei meinen Usern gemacht, die dann
anriefen, weil sie die DLL gelöscht hatten und mein Programm nicht
mehr ging. Seitdem wird bei mir immer abgefragt, wenn ich eine DLL
mitgebe.
Heinz B. schrieb:> Entweder schreibe ich mein Programm so, daß ich die Funktionen> selber programmiere und die DLL gar nicht erst brauche oder ich> nutze halt die Funktionen einer DLL.
Nö. Nicht weit genug gedacht. So eine DLL kann auch z.B. ein Plugin für
irgendeine Funktion sein, und je nach Aufwand unterschiedlich viele
Funktionen zur Verfügung stellen.
Und wenns die DLL nicht gibt, werden die Funktionen halt nicht
angeboten.
Heinz B. schrieb:> Ob man die DLL beim Programmstart oder erst dann, wenn man die> Funktionen braucht, einbindet ist doch wohl egal.
Nein, eben nicht. Beim statischen Einbinden kann das Programm nicht
starten, wenn die DLL nicht vorhanden ist, es kommt genau zu dem Fehler
wie es DerEgon beschrieben hat.
Beim dynamischen Aufruf wird die DLL nur eingebunden, wenn man die
Funktionen wirklich benötigt. Klassisches Beispiel sind Plugins, die
Programme mit zusätzlichen Funktionen ausstatten. Benötigt werden diese
für die Grundfunktionen des Programmes nicht.
Zudem kann man dynamisch geladene DLL's auch wieder aus dem Speicher
entfernen, wenn man sie nicht mehr benötigt und so den Speicher für
andere Dinge freigeben.
Ich habe selbst ein umfangreiches Programm geschrieben, in welchem ich
ausgiebig Gebrauch von dynamisch geladenen DLL's machen. Wenn ich
beispielsweise keine Temperaturen mit einem speziellen Gerät erfassen
muß, dann brauche ich die ganzen Routinen für das Handling des
Temperaturmessgerätes nicht, demzufolge wird wird die DLL die das
erledigt nicht geladen. Wenn ich keinen Report erstellen muß benötige
ich auch nicht die Reportfunktionen, die ebenfalls in einer DLL abgelegt
sind. Jede DLL in diesem Programm hat spezielle Aufgaben, die ich auch
nur in speziellen Fällen benötige. Wenn ich schon bei der Installation
des Programmes sicher sagen kann, das einige Programmfunktionen mit
Sicherheit niemals benötigt werden, dann werden die entsprechenden DLL's
auch nicht installiert und das Programm funktioniert dennoch wie
gewünscht. Mit dem dynamischen Laden der DLL können auch jederzeit die
Programmfunktionen erweitert werden. Der Programmierer muß hierfür nur
ein paar Schnittstellen kennen und kann so eine neue Programmfunktion
hinzufügen. Dabei ist es sogar ihm überlassen in welcher
Programmiersprache er sich dabei austobt.
Heinz B. schrieb:> Entweder schreibe ich mein Programm so, daß ich die Funktionen> selber programmiere und die DLL gar nicht
Nö Du hast den Sinn nicht erkannt und machst damit dein Programm unnötig
unflexibel.
DerEgon hat es hier
Beitrag "Re: Orginaldateiname Visual Studio 2022 App" schon
richtig erkannt.
Statische Linken von DLL's macht eigentlich nur essentiellen
Runtimelibs, prominentes Beispiel die VBRUN300.DLL, Sinn. Bei Programmen
deren Funktionumfang von Anfang fest steht, braucht man weder
irgendwelche .obj, .lib noch .dll mitzugeben, da programmiert man das
einfach in das Hauptprogramm mit rein. Jede zusätzlich notwendige Datei
birgt das Risiko, das der Nutzer seine Programmversion abschießt, wenn
er versehentlich oder aus Unwissenheit eine erforderliche Datei löscht -
was Du ja ganz offensichtlich schon selbst bemerkt hast. Das Problem
wird auch nicht daddurch gelöst, das man die Dateien mit ins
Programmverzeichnis kopiert, da man sie auch dort löschen kann. Wenn ich
alles selbst in der Hand habe, dann sorge ich dafür das das Programm
möglichst immer startet und in seinen Basisfunktionen auch
funktionsfähig ist, selbst dann wenn Dateien fehlen. Es ärgert mich
immer wieder, wenn eine Software nicht benutzt werden kann, weil z.B.
eine simple Konfigurationsdatei fehlt. Ich habe das bei meinen
Programmen so gemacht, das es dann mit Defaulteinstellungen startet und
die Konfigurationsdatei dann aus diesen Einstellungen selbständig
erstellt. Das ist relativ wenig Aufwand, minimiert die Supportanfragen
und hat sich bei mir in gut 30 Jahren bewährt.
Heinz B. schrieb:> Wenn man das ganz gut mit der DLL machen will, bindet man diese> schon vorher als Ressource in die .exe und schreibt sie bei> Programmstart, bzw. Abfrage, ob sie da ist,
Bei einer statisch eingebundenen DLL funktioniert das meist nicht, da
die DLL-Referenzen im EXE-Header stehen und ich gar nicht erst bis zu
meiner Abfrage komme - auch das hat DerEgon richtig beschrieben
Heinz B. schrieb:> Statisch kann man eine .Lib oder .obj einbinden, dynamisch eine> DLL. Daran sehe ich, daß du den Unterschied zwischen .lib und> DLL nicht kennst.
Nein man kann eben auch eine DLL statisch einbinden.
Lib's und obj-Dateien spielen vornehmlich zur Compiletime eine Rolle und
werden schon während des Compiliervorganges aufgelöst und in die EXE
eingebunden. DLL's hingegen können nur zur Laufzeit eingebunden werden,
ob statisch oder dynamisch ist erst mal egal.
Zeno schrieb:> Bei einer statisch eingebundenen DLL funktioniert das meist nicht, da> die DLL-Referenzen im EXE-Header stehen und ich gar nicht erst bis zu> meiner Abfrage komme - auch das hat DerEgon richtig beschrieben
Aha, gut zu wissen.
Ich kenne dann nur dynamisches Einbinden, da bei mir die DLL-Referenzen
halt nicht im Exe-Header stehen. Das Instanzhandle und die Einsprungs-
adressen der Funktionen werden bei mir erst zur Laufzeit ermittelt, soll
heißen, wenn die DLL geladen wird.
Damit hat sich dann das Thema für mich erledigt.