Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Object-Pascal / Delphi-Language (https://www.delphipraxis.net/32-object-pascal-delphi-language/)
-   -   Delphi Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ? (https://www.delphipraxis.net/204622-unter-welchen-bedingungen-wird-ein-system-unit-fix-kompiliert-und-eingebunden.html)

Rollo62 12. Jun 2020 16:05

Delphi-Version: 10.4 Sydney

Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Hallo zusammen,

ich möchte ein System-Unit ändern, und in meiner Library neu kompilieren lassen,
möglichst so das alle statischen Verweise darauf in anderen Orginal System-Units und Libraries umgelenkt werden.

Ich nehme als Beispiel mal FMX.ListView
Delphi-Quellcode:
FMX.ListView.pas // <== dies enthält ein paar Fixes, und das möchte ich in meinem Projekt nutzen

das Unit includiert ein paar weitere Units

Delphi-Quellcode:
Uses
    ...
    , FMX.ListView.Adapters.Base
    , FMX.ListView.Appearances
    , FMX.ListView.Types.pas
    , FMX.ListView.iOS
...
Die nehme ich vorsichtshalber auch mit in mein Projekt, damit auf jden Fall alle zusammenhängenden Units neu kompiliert werden.

Wenn ich die in mein Projektverzeichnis lege, und in meine Projekt DPR einfüge

Delphi-Quellcode:
program T342_Test;

{$R *.dres}

uses
  System.StartUpCopy,
  FMX.Forms,
  UMain_Frm in 'UMain_Frm.pas' {Form_Main},
  UMain_Modules in 'UMain_Modules.pas',
  FMX.ListView in 'FMX.ListView.pas',
  FMX.ListView.Types in 'FMX.ListView.Types.pas',
  FMX.ListView.iOS in 'FMX.ListView.iOS.pas',
  FMX.ListView.Adapters.Base in 'FMX.ListView.Adapters.Base.pas',
  FMX.ListView.Appearances in 'FMX.ListView.Appearances.pas';

{$R *.res}

begin
  Application.Initialize;
  Application.CreateForm(TForm_Main, Form_Main);
  Application.Run;
end.
.. dann scheint es zu funktionieren wie gewünscht.
Der Debugger kann die DCU-Units richtig zuordnen, die Debug-Breaks scheinen zu stimmen.

D.h. ich vermute das die neu kompilierten Units auch korrekt in meinem Projekt angemommen sind.

Erste Frage:
Wie kann ich sicher sein das nicht ein anderes System-Unit noch die Orginale Unit benutzt,
und ich zwei "DCU-Versionen" in mein Projekt einbinde ?


Ich würde dieses Chaos in der DPR gerne aufräumen, und leider erlaubt die IDE/Compiler keine Unterverzeichnisse an bestimmten Stellen.
Deshalb mache ich das sicherheitshalber immer so wie oben.

Meine zweite Frage ist,
wie könnte ich diese Fixes besser zusammenfassen ?,
am Besten so das ich nicht alle Units (keine) in der DPR auflisten muss.


A.) Meine Versuche das in Unterverzeichnisse zu legen funktioniert anscheinend nicht zuverlässig
Project\TestProject.dpr
Project\Fixes\FMX.ListView.pas
...


B. Meine Versuche nur eine zentrale Fixes.pas Unit in das Projektverzeichnis zu legen funktioniert anscheinend auch nicht sicher.
Project\TestProject.dpr
Project\Fixes.pas //<=============
Project\Fixes\FMX.ListView.pas
...

mit der zentralen Unit in der DPR

Delphi-Quellcode:
unit Fixes;

interface

Uses
    FMX.ListView
  , FMX.ListView.Types
...

implementation

end.


C. Ich habe auch probiert die Orginal-Units per include in Wrapper-Units zu laden,
um so zumindest verschiedene IDE-Versionen zu kapseln, so in der Art
Delphi-Quellcode:
unit FMX.ListView;

{$IF    DEFINED( RX1040 ) }
{$I FMX.ListView_Rx1040 }
{$ELSEIF DEFINED( RX1033 ) }
{$I FMX.ListView_Rx1033 }
{$ENDIF }
Das geht wenn man in den Varianten-Units den Header weglässt, löst aber nicht mein eigentliches Problem, das ich die Files genre besser sortieren würde.

Bin ich der Einzige dem solche Chaos-Anordnungen auf die Nerven gehen,
oder hat vielleicht jemand einen guten Tipp wie man das Ganze besser, sauberer organisieren könnte ?

himitsu 12. Jun 2020 18:54

AW: Unter welchen Bedingungen wird ein System-Unit neu kompiliert ?
 
Die werden nie neu kompiliert. Zum Kompilieren werden die DCUs verwendet und nicht die PAS, drum stehen die hauseigenen PAS auch nicht im Suchpfad für den Compiler.
Wenn, dann mußt du das selber nachen und deren DCU und Debug-DCU aktualisieren. Uns mit viel Pech auch noch die BPLs und all deren Abhängigkeiten.

Für die eigene Verwendung kann man die Suchpfade so anpassen, dass die eigene Datei vor denen des Delphi gefunden werden.
Aber das ersetzt nur dort wo kompiliert wurde, also z.B. nicht:
  • du erstellst dir eine System.Classes.pas und die steht im Suchpfad weiter vorne
    • alternativ kann man in der DPR diese Unit aufnehmen, bzw. im Projektmanager,
      wo die Unit dann inkl. Pfad direkt gewählt wird
  • dann wird in den USES von dir die neue Datei benutzt
  • aber wenn du nicht auch die System.Forms.pas kopiert hast, dann verwendet deren Kompilat natürlich weiterhin die originale Classes

Rollo62 13. Jun 2020 08:48

AW: Unter welchen Bedingungen wird ein System-Unit Fiix kompiliert und eingebunden ?
 
Zitat:

Zitat von himitsu (Beitrag 1467164)
Die werden nie neu kompiliert.

Ja richtig, das meinte ich auch nicht (hab mal den Titel angepasst um das besser zu beschreiben).

Sagen wir mal es gibt eine Orginal-DCU der FMX.ListView.pas welche normalerweise statisch gelinkt wird.
Binde ich jetzt meine gefixte FMX.ListView.pas in meine Projekt-DPR ein, dann wird diese neu-kompilierte-DCU zum Projekt gelinkt, statt der statischen Orginal-DCU.
Durch den gleichen Namen der FMX.ListView.pas sollte gewährleistet sein das es im Projekt nur EINE Version der FMX.ListView-DCU geben kann (also in dem Fall nur meine, gefixte Version).

Soweit so gut.

1. Frage:
Ist das so, oder könnten auch 2 FMX.ListView-DCU's (alt/neu) gleichzeitig in einem Projekt existieren ?
Wenn z.B. andere Orginal-DCU's statisch die alte Orginal-DCU einbinden.
Wie kann ich sicher sein das wirklich nur die gefixte DCU gelinkt ist.

Leider scheint das nicht immer zu funktionieren wenn der Suchpfad nicht im .DPROJ Haupt-Verzeichnis liegt.
Dann habe ich keine Chance den Pfad zu meiner gefixten FMX.ListView.pas anzugeben, und es wird
doch die orginale DCU, oder noch schlimmer beide Versionen gelinkt.
Das könnte sich durch nicht mehr passende Breakpoints zeigen (die blauen Break-Punkte sind verschoben).

Gibt es noch andere Methoden um solche "verschobenen" Breakpoints, und falsche statische Links zu finden und zu Vermeiden ?

2. Frage:
Ich kenne nur die obige Methode (in jedem .DPROJ Hauptverzeichnis) um sicher solche Fixes zu linken und einzubauen.
Ich hoffe aber das es doch irgendeine Möglichkeit gibt diese gefixten FMX.ListView.pas irgendwo in Unterverzeichnisse zusammenzufassen, so dass sie noch sicher gelinkt werden.

Z.B. wäre auch denkbar alle diese Fixes in einem zentralen DCP/LIB zu linken,
und dann den Projekten nur die eine DCP hinzuzulinken.
Ich vermeide aber möglichst solches vorkompiliertes, statisches Linken, weil das oft mehr Probleme bringt als löst (man vergisst gerne solche statischen DCP/LIB zu aktualisieren).

Mein Favorit sind aber leichtgewichtige Units, die immer neu kompiliert werden, statt schwerer, statischen DCP/LIB Files, welche nicht immer neu kompiliert werden.
Mit Kompilierzeiten habe ich weniger ein Problem, so dass ich keine Precompiled-Libraries brauche.

philipp.hofmann 13. Jun 2020 09:12

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Der Pfad in deiner Projektdatei ist falsch bzw. zeigt nur auf das Hauptverzeichnis. Wenn Du die Datei in

Delphi-Quellcode:
Project\Fixes\FMX.ListView.pas
liegen hast, muss es
Delphi-Quellcode:
FMX.ListView in 'Fixes\FMX.ListView.pas',
heißen.

Ansonsten sehe ich keinen Grund, warum hier irgendetwas nicht funktionieren sollte und solche Fixes habe ich immer eingebunden. Meist sogar abhängig vom OS und der Delphi-Version:

Delphi-Quellcode:
  {$IFDEF ANDROID}
    {$IFDEF VER330}
      FMX.Media.Android in 'utils\10.3\FMX.Media.Android.pas',
      System.Android.Bluetooth in 'utils\10.3\System.Android.Bluetooth.pas',
    {$ENDIF}
  {$ENDIF}

Dabei ist wichtig, dass man diese OS-abhängigen Überschreibungen irgendwo nochmals sichert (ich führe sie in der Projekt-Datei zweimal auf, einmal auskommentiert und einmal einkommentiert, weil der einkommentierte Teil beim Umschalten zwischen den OS oftmals kaputt gemacht wird.

himitsu 13. Jun 2020 10:06

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
1. in dem Projekt gibt es in deinem DCU-Ausgabeverzeichnis nur eine DCU der Unit A.

Wenn du in deinen USES den Unitnamen von A angibst, dann wird deine DCU benutzt,

aber, verwendest du noch andere Dateien, wo du die originale DCU von DELPHI verwendest, die in sich eine Unit A einbinden,
dann sind die ja bereits fertig kompiliert und haben daher natürlich weiterhin die originale DCU A gelinkt,
womit es dann in deiner EXE zwei Mal die A gibt.

Willst du etwas Fixen, und du bist nicht der Einzige, welcher diese Unit linkt und der Fix soll überall rein,
dann mußt du also alle Units kopieren und neu kompilieren, auch Jene, welche diese Unit ebenfalls verwenden und die auch diese verwenden usw.



Da kommt man womöglich/vermutlich mit Hooks besser, wenn man nicht der Einzige ist, der diese Unit einbindet.

dummzeuch 13. Jun 2020 10:16

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von himitsu (Beitrag 1467175)
aber, verwendest du noch andere Dateien, wo du die originale DCU von DELPHI verwendest, die in sich eine Unit A einbinden,
dann sind die ja bereits fertig kompiliert und haben daher natürlich weiterhin die originale DCU A gelinkt,
womit es dann in deiner EXE zwei Mal die A gibt.

Fertig compiliert <> fertig gelinkt.

Beim Compilieren entstehen DCU-Dateien. Diese nimmt dann der Linker und fügt sie zu einem Executable zusammen. Es kann immer in einem Exectuable nur eine DCU mit dem jeweiligen Unit-Namen geben.

Insofern ist sichergestellt, dass, wenn das Programm eigene (veränderte) Units verwendet, auch nur diese verwendet werden.

Delphi.Narium 13. Jun 2020 10:26

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von himitsu (Beitrag 1467175)
1. in dem Projekt gibt es in deinem DCU-Ausgabeverzeichnis nur eine DCU der Unit A.

Wenn du in deinen USES den Unitnamen von A angibst, dann wird deine DCU benutzt,

aber, verwendest du noch andere Dateien, wo du die originale DCU von DELPHI verwendest, die in sich eine Unit A einbinden,
dann sind die ja bereits fertig kompiliert und haben daher natürlich weiterhin die originale DCU A gelinkt,
womit es dann in deiner EXE zwei Mal die A gibt.

Willst du etwas Fixen, und du bist nicht der Einzige, welcher diese Unit linkt und der Fix soll überall rein,
dann mußt du also alle Units kopieren und neu kompilieren, auch Jene, welche diese Unit ebenfalls verwenden und die auch diese verwenden usw.



Da kommt man womöglich/vermutlich mit Hooks besser, wenn man nicht der Einzige ist, der diese Unit einbindet.

Oder der Kompiler gibt den Hinweis aus, dass Unit X mit einer anderen Version von A kompiliert wurde, und er bricht den Kompiliervorgang ab.

Zuweilen stellt Delphi von ganz alleine beim Kompilieren fest, dass es da einen Konflikt gibt und weist darauf hin.

Zumindest Delphi 7 und älter konnten sowas. Geht das heute nicht mehr? ;-)

Eigentlich ist wichtig, dass man die veränderten Sourcen ins Projekt aufnimmt und sicherstellt, dass der Kompiler nur diese und die zugehörigen DCUs finden kann.

D. H.: Die "Originale" sollten in allen Pfadangaben hinter den eigenen, veränderten Sourcen / DCUs zu finden sein (oder im Idealfall garnicht zu finden sein).

Wurde eine Unit mit Deiner veränderten FMX.ListView.pas im Uses kompiliert und Dein Projekt enthält eine weitere Unit, die mit der originalen FMX.ListView.pas im Uses kompiliert wurde, so sollte der Kompiler dies bemerken und Dich darauf hinweisen.

Im Zweifelsfalle nehme ich immer alle Units in die DPR auf, die "irgendwo" in einer Unit des Projektes per Uses aufgerufen werden und bei denen die Möglichkeit eines Konfliktes bestehen könnte. Damit habe ich bisher immer alle Konflikte auflösen können (auch wenn die DPR dadurch schonmal etwas unübersichtlich lang werden kann).

Der DCU-Ausgabepfad ist bei mir immer gesetzt, so dass die Original-DCUs eventuell neu zu kompilierender "delphieigener Units" nicht überschrieben werden.

himitsu 13. Jun 2020 11:01

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Es kommt auch drauf an, wie viel man mit Packages und DLLs arbeitet.

Bei uns wurde mal eine Unit doppelt ins System einkompiliert, mit dem Ergebnis dass ein Kollege tagelang einen Fehler suchte, wo ich am Ende den Fehler fand, dass die globale Variable auch doppelt war.
An einer Stelle gesetzt, geprüft war sie auch voll, aber von einer anderen stelle aus abgerufen war sie plötlich leer ... nochmal geprüft und die war wieder voll. :stupid:

[edit]
OK, stimmt ... fast vergessen ... in einem Modul sind UnitNamen eindeutig. (EXE oder DLL, wobei BPLs als gesamtsystem zusammengehören)
Bei uns war die Unit in zwei DLLs, anstatt in einer gemeinsamen BPL.

Aber Dank Default-Namespases kann man das Problem mit der Eindeutigkeit umgehen, indem man Einen definiert und seine Unit damit erweitert. :angle2:

Rollo62 13. Jun 2020 12:15

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Hallo Phillip,

das mit dem Unterverzeichnis hatte ich auch früher probiert.
Es gab aber trotzdem nicht passende Breakpoints im Projekt.

An Alle, danke für die Kommentare.
Ich sehe es ja genauso, aber es geht bei mir nicht um Dll oder Bpl.
Ich habe auch keine statischen Librries drin, alles ist möglichst mit BuildAll neu gebaut.
In der Regel mache ich auch ein Clean vorher, so das es keine DCU Leichen geben sollte.

Trotzdem sehe ich manchmal verrutschte Breakpoint.

Mir ist aber gerade eingefallen das ich doch 2-3 eigene Controls in der IDE installiert habe.
Diese könnten die Ursache sein, wenn nicht neu kompiliert ist das der Einzige gelinkte Code bei mir, der mir einfällt.
Das kann der Grund sein, kann aber gerade nicht testen.

Nochmal zu den Unterverzeichnissen, funktioniert das immer 100% sicher, denn das war vor ein paar Jahren mein erster Versuch.
Wegen Linkprobleme mit verrutschten Breakpoints bin ich aber davon abgekommen.
Können solche statischen Libraries noch an anderen Stellen auftreten ?
Wie bekommt man sowas mit, denn Warnings sehe ich nicht.

Rollo62 13. Jun 2020 12:22

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Das was Thomas zu Compiler Linker schreibt sehe ich auch so.
Was mir dazu einfällt wäre eine Sitation wo eine Optimierung z.B. die Unit in einem Unterverzeichnis nicht linkt.
Weil Compiler Linker denken die ist nicht benutzt.

Wäre sowas denkbar ?

Dann müsste man in jedem Fix eine DummyRoutine aufrufen, damit es gelinkt wird.

dummzeuch 13. Jun 2020 12:27

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von Rollo62 (Beitrag 1467191)
Das was Thomas zu Compiler Linker schreibt sehe ich auch so.
Was mir dazu einfällt wäre eine Sitation wo eine Optimierung z.B. die Unit in einem Unterverzeichnis nicht linkt.
Weil Compiler Linker denken die ist nicht benutzt.

Wäre sowas denkbar ?

Dann müsste man in jedem Fix eine DummyRoutine aufrufen, damit es gelinkt wird.

Eigentlich nicht. Wenn der Compiler Sourcecode und DCU findet, prüft er, welches neuer ist, und compiliert dann neu. Wenn eine Unit nicht benutzt wird, spielt es keine Rolle. Wenn Du wissen willst, ob eine Unit in ein Executable eingebunden wird, kannst Du in das .MAP-File des Linkers gucken. Da steht allerdings nur der Unitname drin, nicht der komplette Dateiname. Es gibt auch die Möglichkeit zur Laufzeit die Liste der Units durchzugehen, aber auch das liefert wieder nur den Unitnamen, nicht den Dateinamen.

himitsu 13. Jun 2020 16:26

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Wenn jemand die PAS von Delphi verändert, dann passen sie natürlich nicht mehr zu den Debuginfos des Compilats und Zeilen können verrutschen.
Kann natürlich auch mal sein, dass der Hersteller bereits unpassende Dateien ausgeliefert hat.

z.B. hab ich bei mir abgestellt, dass schreibgeschützte Dateien im Editor schreibgeschützt sind, damit ich bequemer dort kopieren/ausschneiden/umformatieren/... kann, wenn ich in den Sourcen mal was suche.
Allerdings lassen sich die Dateien bei mir dennoch nicht speichern, womit ich da keine Angst haben muß, dass was verändert wird, auch wenn die blöde Recovery-Funktion echt nervt, weil sie dort ins Verzeichnis schreiben will.
Andere haben da mehr Probleme, welche auf die "schlaue" Idee kommen Delphi wo anders zu installieren, wo der Pfad nicht durch Zugriffsrechte geschützt ist.

jziersch 14. Jun 2020 20:17

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Ich weiß jetzt nicht ob dies Dein Problem löst, ich habe aber für ein ähnliches Problem einen Unit-Alias auf eine umbenannte Unit mit Erfolg eingesetzt. Dies hilft auch bei der Unit FireDAC.VCLUI.Wait welche die IDE auch zu einem FMX Projekt standhaft hinzufügt.

Rollo62 15. Jun 2020 06:45

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von jziersch (Beitrag 1467254)
Ich weiß jetzt nicht ob dies Dein Problem löst, ich habe aber für ein ähnliches Problem einen Unit-Alias auf eine umbenannte Unit mit Erfolg eingesetzt. Dies hilft auch bei der Unit FireDAC.VCLUI.Wait welche die IDE auch zu einem FMX Projekt standhaft hinzufügt.

Dankesehr für den Vorschlag, habe auch das hier von Thomas dazu gefunden.
Sowas wie "Unit-Alias" hatte ich bisher noch gar nicht auf dem Schirm, interessant.

Mit geht es insbesondere um die falsch zugeordneten Breakpoints, die mal auftreten können.
Wenn die beim Debuggen der System-Units auftreten könnte ich das ja noch verstehen,
aber beim Debuggen der gefixten Units, die ja definitiv neu kompiliert und eingebunden habe,
sollte das doch nicht passieren.
Das Seltsame ist ja das dies mal auftreten sein kann, und dann auch mal wieder weg ist.
Bisher hat es mit einen kompletten Clean des Projektes (Batch-Datei die alle Leichen entfernt, sogar die Verzerichnisse) immer geholfen.
Das trat auch immer nur selten auf, und ich konnte mir das durch Fehler im Build-Vorgang erklären.
Diesmal ist es aber hartnäckiger.
Deshalb Suche ich gerade nach den Ursachen und Möglichkeiten wie man das zweifelsfrei weg bekommt.

Ich habe als Ursache noch meine Design-Komponenten im Verdacht, die ich womöglich nochmal neu builden müsste.
Diese haben allerdings gar nichts mit FMX.ListView zu tun, aber das Problem der Verschiebung der Breakpoints könnte sich dadurch ja trotzdem darüber erklären lassen.
Das wäre meiner Meinung nach die einzige Stelle bei mir wo sowas herrühren könnte, weil ich
ansonsten Alles aus Sourcen neu kompiliere.

Das der Fehler aus den Rx10.4 Orginal-Units/statischen Libraries kommt glaube ich eher nicht,
könnte aber natürlich auch der Fall sein.
Deshalb die Frage wie man sowas exakt herausfinden könnte (Compiler/Linker geben bei mir ja keine Warnung).

Bin aber erst noch anderweitig beschäftigt, muss ich ein bischen später checken.

Rollo62 15. Jun 2020 18:04

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Ich denke Schuld and den verschobenen Breakpoints war die Design-Komponente,
welche eine gemeinsame Unit mit hauptsächlich globale Konstanten eingebunden hat.
Die Konstanten hatte ich mal ergänzt und umgebaut, aber vergessen den Design-Unit mit upzudaten.

Ich habe diese Unit jetzt neu gebuildet und installiert, die Breakpoints stimmen wieder.
Alle Fixes liegen jetzt wie bisher in der DPR, und im Verzeichnis neben der DPR.
Delphi-Quellcode:
Uses
  ...
  , FMX.ListView in '_FmxFixes\FMX.ListView.pas'
  ...
  ;
Das funktioniert soweit, so hatte ich es auch bisher.


Zum Thema Aufräumen der Units aus der DPR bin ich aber noch nicht ganz am Ziel.
Ich möchte die DPR möglichst sauber halten, aber das Zusammenfassen aller Fixes in einer Unit
z.B. FmxFixes.pas
Delphi-Quellcode:
//DPR
Uses
  ...
  , FmxFixes in '_FmxFixes\FmxFixes.pas' //<== Da kann man es genau spezifizieren
  ...
  ;

//FmxFixes.pas

Uses
  ...
  , FMX.ListView //<== hier nicht mehr, die gefixten Units MÜSSEN wohl neben der DPR liegen
  ...
  ;
A. Das kompiliert eben leider nicht.
Wenn an anderer Stelle FMX.ListView benutzt wird, dann nimmt er das orginale System-Unit.

Ich möchte aber gerade den ganzen Müll aus der DPR entfernen, und möglichst zentral einbinden,
z.B. über FmxFixes.pas, FmxFixes.inc, o.ä.


B. Abhilfe schafft, wenn ich im Search Library als ersten Suchpfad die _FmxFixes mit angebe,
dann wird im Unterverzeichnis _FmxFixes zuerst gesucht:
Delphi-Quellcode:
  _FmxFixes\
Vergesse ich das Unterverzeichnis kompiliert es u.U. auch, aber keiner merkt es.

Kompilieren, Linken Ausführen funktioniert.

Wenn ich jetzt aber in irgendeiner anderen Unit die auch FMX.ListView benutzt (oder auch in der FmxFixes.pas selbst),
dieses File öffne (mit Ctrl-Enter oder Context-Open File at Cursor),
dann wird NICHT das gefixte, sondern das Orginal-Unit geöffnet.
Im Editor können auch mal beide FMX.ListView.pas Units geöffnet sein, was mich extrem nervt,
denn das Öffnen per IDE zeigt in der Regel immer das Falsche an.

Genauso hatte ich es damals auch mal beim Debuggen festgestelt, weshalb ich die Lösung oben mit allen Fixes neben der DPR direkt in die DPR eingebunden einsetze.
Es war für mich kein Verlass darauf von wo die IDE sich gerade die Units holt, selbst wenn das der Compiler/Linker womöglich richtig macht.
Die Gefahr in der IDE das Falsche File zu Editieren ist sehr hoch.

C. Fixes im Unterverzeichnis, aber direkt in die DPR einbinden:
Wenn ich jetzt die Fixes in den Unterveerzeichnissen angebe scheint es zu funktionieren, auch in der IDE (dankesehr nochmal an Phillip), ich werde das mal weiter beobachten.
Ich meine es gab da auch vertauschte Units beim Debuggen.
Meine Lieblingslösung wäre das aber noch nicht, weil die DPR zig Fixes enthalten muss.

Deshalb hatte ich es vor Jahren schonmal aufgegeben, ich fürchte fast ich muss den ganzen Fixes-Müll in der DPR behalten. :stupid:

Es ist wirklich zu blöd das Delphi keine Verzeichnisse im Unit-Namen unterstützt, nur in der DPR.

Delphi.Narium 15. Jun 2020 18:33

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Ja, Du musst die Fixes in der DPR behalten.

Aber:

Man kann das ja auch einfach mal alles in 'ne Alle_Meine_Fixes.inc packen und dann nur die in die DPR stecken.

Die DPR wird so "nur eine Zeile länger als normal" und die Includedatei kann man in allen Projekten nutzen. Muss dann für die eigenen Fixes nur eine Stelle pflegen und vergisst dann nicht mal in 'nem Projekt das eine oder andere nachzutragen, zu entfernen, ... derweil: Steht ja alles in einer Includedatei für alle Projekte.

Man müsste mal prüfen, ob die IDE damit auch zurechtkommt und Strg+Enter immer zur richtigen Datei (hier also der in der Includedatei aufgeführten) geht.

Nur mal so als Idee zum Probieren, eventuell bringt es Dich ja ein Stückerl weiter.

Rollo62 15. Jun 2020 19:02

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Ja so was wäre schon besser sortiert.
Zumindest bleibt die DPR dann maximal sauber, und die .Inc Datei könnte die passenden Fixer mit IFDEF selektieren.

Besser wird es wohl nicht gehen.

Rollo62 16. Jun 2020 10:33

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Hallo Delphi.Narium,

ich habe es gerade nochmal gecheckt.
Auch das scheint nicht zuverlässig zu funktionieren.
Wenn ich das Projekt aufräume, und nur alle Uses im Include ergänze

Delphi-Quellcode:
program TTest;

{$R *.dres}

uses
  System.StartUpCopy,
  FMX.Forms,
  UMain_Frm in 'UMain_Frm.pas' {Form_Main},
  UMain_Modules in 'UMain_Modules.pas',
  UMain_Pages in 'UMain_Pages.pas',
{$I '_FmxFixes\_FmxFixes.inc'}    //<== hier sind ale Fixes zusammengefasst drin
  ;

{$R *.res}

begin
  Application.Initialize;
  Application.CreateForm(TForm_Main, Form_Main);
  Application.Run;
end.


// Mit _FmxFixes.inc
  , FMX.ListView.iOS in '_FmxFixes\FMX.ListView.iOS.pas'
  , FMX.ListView in '_FmxFixes\FMX.ListView.pas'
  , System.iOS.Sensors in '_FmxFixes\System.iOS.Sensors.pas'

oder auch wenn die Units selber direkt mit eingebunden werden

Delphi-Quellcode:
program TTest;

{$R *.dres}

uses
  System.StartUpCopy,
  FMX.Forms,
  UMain_Frm in 'UMain_Frm.pas' {Form_Main},
  UMain_Modules in 'UMain_Modules.pas',
  UMain_Pages in 'UMain_Pages.pas',
  FMX.ListView.iOS in '_FmxFixes\FMX.ListView.iOS.pas',
  FMX.ListView in '_FmxFixes\FMX.ListView.pas',
  System.iOS.Sensors in '_FmxFixes\System.iOS.Sensors.pas',
  ;

{Main_Styles_Form}

{$R *.res}

begin
  Application.Initialize;
...

Es kompiliert und läuft Beides.

Problem:
In beiden Fällen kann ich in irgendeiner Unit die FMX.ListView benutzt dieses File öffnen,
aber es öffnet sich immer die orginale Unit in der IDE, nicht der Fix.

Die einzig zuverlässige Lösung ist und bleibt anscheinend:
- gefixte Units müssen im gleichen Verzeichnis der .DPR /.DPROJ liegen
- alle gefixten Units müssen direkt in das Projekt, in die .DPR eingebunden werden

Nur dann scheinen Compiler/Linker UND IDE/Debugger immer die richtige Unit zu benutzen.

Mal abgesehen davon, das ein Einbinden von Includes das Einfügen von Files im Designer durcheinanderbringt, und regelmäßig die .DPR STruktur zerstört.
Was aber das kleinere Problem wäre.

Ok, ich gebe mal wieder auf, wie schon zuvor, und lasse den Müll eben in der .DPR und im Verzeichnis.
Die Hoffnung stirbt zuletzt.

Delphi.Narium 16. Jun 2020 11:31

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Ehrlichgesagt verstehe ich nicht, wieso Units, die in ein Projekt aufgenommen werden und dadurch in der DPR stehen, Müll sein sollen.

Delphi ist nunmal so konstruiert, dass das das delphikonforme Vorgehen darstellt. Was ist da so schlimm dran?

Habe bei mir seit ca. 25 Jahren die ins Projekt aufgenommenen Units in der DPR stehen. Habe damit nie Probelme gehabt. Und da ich in der DPR sowieso nur sehr selten eigenen Quelltext einfügen muss oder dort irgendwas programmatisch lösen muss, sehe ich nur sehr selten in die DPR.

Eigentlich ist die DPR der Quellcodeteil eines Projektes, mit dem ich am wenigsten zu tuen habe. Warum soll es da schlimm sein, wenn im Uses halt eben mal viele Zeilen stehen. Quellcode finde ich hinter dem ersten begin. Das ggfls. per Strg+S zu suchen ist auch nicht soviel Aufwand.

Achso: Bisher ist die Erfahrung mit vielen in die DPR aufgenommenen Units dergestalt, dass das Kompilieren schneller geht, da der Kompiler nicht erst in einer mehr oder weniger langen Pfadliste nach was passendem suchen muss. Er bekommt genau gesagt, was er gefälligst zu nehmen hat. Konflikte mit gleichnamigen Units in unterschiedlichen Verzeichnissen, die dann auch mal verwechselt werden können, gibt es so auch nicht.

Warum mit sehr viel Aufwand eine nicht den Delphi-/IDE-Vorgaben entsprechende Lösung suchen, wenn es eine seit 25 Jahren funktionierende, den Delphi-/IDE-Vorgaben entsprechende Lösung, gibt?

Naja: Wenn die IDE die falsche Datei öffnet, liegt es vermutlich daran, dass sie zuerst bei den "eigenen" Sourcen sucht und erst dann bei den in der DPR eingebundenen. Ist das ein Bug oder ein Feature? Kann man das eventuell mal beim Hersteller als feature request "einreichen"?

Rolf Frei 16. Jun 2020 13:19

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von Rollo62 (Beitrag 1467155)
Bin ich der Einzige dem solche Chaos-Anordnungen auf die Nerven gehen,
oder hat vielleicht jemand einen guten Tipp wie man das Ganze besser, sauberer organisieren könnte ?

Ganz einfach. Mach dir irgendwo ein neues Verzeichnis "BugFixes\10.4". Alle Delphi Untis die du mit Fixes ergänzt kopierst du dir hier rein. Das Verzeichnis fügst du dann im globalen Suchpfad an erster Stelle ein, also noch vor den Delphi eigenen Verzeichnissen (lib, etc). So wird dann immer die gefixter Version verwendet und nicht mehr die verbugte Originalversion. In deinen Prokjekten musst do so nichts weiter machen.

Rollo62 16. Jun 2020 13:52

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von Delphi.Narium (Beitrag 1467417)
Ehrlichgesagt verstehe ich nicht, wieso Units, die in ein Projekt aufgenommen werden und dadurch in der DPR stehen, Müll sein sollen.

Ganz einfach, da habe ich mehrere Gründe:

1. Weil das Verwalten der Fixes für mich unnützer Ballast ist.
Den bearbeite ich normalerweise nur einmal (pro Version), im Idealfall,
und will den dann komplett vergessen.
So muss ich aber in jedem Projekt, und bei jedem Update (wo ich .DPROJ neu anlegen muss,
diesen ganzen Kram wieder händisch anfassen.
Gut, die manuelle Kontrolle hat auch ihre Vorteile, aber das Copy-Paste bringt mehr Nachteile.

2. Mit "Müll" meine ich das in der .DPR ohne Fixes stehen bei mir ca. 4-5 Units pro Projekt.
Je nachdem welche Features ich nutze bekommen ich aber 5-20 Fixes-"Müll" mit da rein.
Das gleiche gilt für das Hauptverzeichnis der Projekte.
Weil ich die Fixes anscheinend nur da reinkopieren kann, damit Compiler/Linker/IDE/Debugger damit klarkommen, kommt auch dort ungewünschter "Müll" rein.
Sonste hätte ich dort ca. 10 Files pro Projekt.
Erschwerend kommt da hinzu das ich viele Mobile-Projekte habe, und dort oft .DPROJ neu anlegen muss,
damit neue Features übernommen werden.
Früher reichte eine .DPROJ bei mir auch mehrere Jahre, unter Windows, die Zeiten sind vorbei.

3. Ich benutze gerne immer gleiche, funktionierende Konfigurationen, wo die Fixes eben gut
aufeinander abgestimmt sind.
Durch den "Müll" im Projekt ist es aber kaum wartbar.
Ich mache es im Moment so das ich die benötigten Fixes ausserhalb manage, und dann den Projekten nur die funktionierenden Kombinationen einspiele.


4. Weil ich gerne die ganzen Features und Fixes global steuern und konfigurieren möchte.
Also in der Art:
Projekt braucht FMX.ListView, Projekt braucht MapView, etc. dann nur die nötigen Fixes reinbauen.
Falls eben möglich benutze ich dafür solche Defines, um Features einfach und gut verständlich ein/ausschalten kann:
Delphi-Quellcode:
{$DEFINE _X_HAS_FEATURE_NOTIFICATION_LOCAL }
{$DEFINE ___HAS_FEATURE_NOTIFICATION_REMOTE }
{$DEFINE _X_HAS_FEATURE_TTS_SPEAK}
{$DEFINE _X_HAS_FEATURE_MEDIA_AUDIO_PLAY }
{$DEFINE ___HAS_FEATURE_MEDIA_AUDIO_RECORD }
{$DEFINE ___HAS_FEATURE_WIFI }
{$DEFINE ___HAS_FEATURE_WIFI_NETWORK_INFO }  // Allow the retrieval see S4.Core.Net.Ssid.iOS
Dadurch können sich meine Module voll-automatisch richtig konfigirieren,
nur eben der "Müll" in der .DPR bleibt reine Handarbeit.
Die Gefahr ist, das man was vergisst, und dann gibt es nicht immer eine klare Fehlermeldung.
Die App crasht vielleicht weil irgend ein Fix vergessen wurde, oder veraltet ist.

5. Weil Fixes auch ständig upgedatet werden müssen, muss ich dann zig Kopien, in zig. Projekten updaten.
Ich habe mir dafür ein Kopier-System gebaut, so dass ich aus einem Fixes-Master die aktuellen Fixes in jedes Projekt updaten kann.

6. In Erweiterung zu 5.) verwaltet das dann auch verschiedene Ide-Versionen, also
Rx10.3.3, Rx.10.4.0, etc., so das jede IDE die zu ihr passenden Fixes bekommt.

Mir fallen bei längerem Nachsinnen womöglich noch mehr Gründe ein,
aber das hier reicht schon mehr als aus um mir Bauchschmerzen zu machen.


@Rolf Frei
Danke für den Vorschlag, genau das möchte ich ja machen.
Leider kommen damit z.B. Ide/Debugger nicht immer klar, wie unten beschrieben,
auch wenn Compiler/Linker etwas Lauffähiges produzieren.

Ich hatte schon oft in Sourcen gedebuggt und gesucht, nur um dann nach Stunden festzustellen das die IDE mal wieder das falsche File geladen hatte.
Deshalb kann ich die Files eben nicht in Unterverzeichnisse zusammenfassen, sondern es muss wohl Alles zusammen bei .DPR und .DPROJ im Verzeichnis liegen.
Nur dann habe ich die Gewähr das Compiler/Linker/Ide/Debugger IMMER das richtige File öffen/nutzen.

Delphi.Narium 16. Jun 2020 14:44

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
@Rollo62

Ok, Dir geht es darum Redundanzen zu vermeiden.

Quasi im Idealfall: Ein Fix ist einmal ein Aufwand, für alle betroffenen Projekte gleichzeitig.

Ist er obsolte geworden, wird er genau einmal entfernt, für alle Projekte gleichzeitig.

Unter Müll verstehst Du letztlich alles das, was erforderlich ist, um Fehler in den Delphisourcen zu umgehen, vorübergehend zu beheben, bis sie im Original beseitigt worden sind.

Und ja: Es geht Dir um einen möglichst geringen Aufwand für die ganze Chose, darum, Dich um die eigentliche Entwicklungsaufgabe kümmern zu können und nicht, Dich mit nicht unerheblichem Aufwand um die "Umschiffung fremder Fehler" kümmern zu müssen und die bei der "Umschiffung" möglichen Fehler möglichst Richtung 0 zu reduzieren.

Eine absolut legitime und sinnvolle Vorgehensweise. :thumb:

Rolf Frei 16. Jun 2020 15:12

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Wenn du das so machst wie ich geschrieben habe und sowohl den Library-Suchpfad als auch optional den Browse-Suchpfad mit den neuen Verzeichnis ergänzt (Globale Einstellungen: Menü Tools/Options/Language/Delphi Options/Library), sollte das problemlos funktionieren. Den Browsepfad musst du im Prinzip nicht anpassen, solange dein BUGFIX Verzeichnis die Sourcen enthält. Ich nutze das schon seit Delphi 1 so und hatte noch nie ein Problem damit.

Deine Projekte benötigen nichts eintragen! Lösche da alle deine Verküpfungen die gefixten Units und alle lokalen im Projekt herumschwirrenden DCU's. Das macht keinen Sinn, dass du das pro Projket nochmals machen willst. Die gefixten Versionen werden automtisch genutzt (kompiliert), wenn diese Pfade in den globalen Einstellungen richtig gesetzt sind und dein BUGFIX Pfad VOR den Delphi Pfaden ist.

Wenn du irgendwann mal wieder die falsche Unit angezeigt bekommst, hast du zu 100% eine Verknüpfung auf die Sourcen in deinem Projekt hinterlegt. Die Projektpfade (Projektoptionen) haben immer Vorrang vor den globalen Einstellungen und wenn du da einen Pfad auf die Originalsourcesn drin hast, ist es logisch, dass diese angezeigt werden.

Rollo62 16. Jun 2020 16:16

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von Rolf Frei (Beitrag 1467454)
Wenn du das so machst wie ich geschrieben habe und sowohl den Library-Suchpfad als auch optional den Browse-Suchpfad mit den neuen Verzeichnis ergänzt (Globale Einstellungen: Menü Tools/Options/Language/Delphi Options/Library), sollte das problemlos funktionieren.

Na gut, will ich dann auch nochmal mit globalen Einstellungen probieren.

Zitat:

Zitat von Rolf Frei (Beitrag 1467454)
Den Browsepfad musst du im Prinzip nicht anpassen, solange dein BUGFIX Verzeichnis die Sourcen enthält.

Das tut es, ich habe quasi nur Sourcen, und keine vorkompilierten DCU's

Zitat:

Zitat von Rolf Frei (Beitrag 1467454)
Deine Projekte benötigen nichts eintragen! Lösche da alle deine Verküpfungen die gefixten Units und alle lokalen im Projekt herumschwirrenden DCU's.

Ich habe früher auch nur Alles in den Optionen/Tools konfiguriert, bin aber seit geraumer Zeit davon ab.
Mittlerweile habe ich alle Pfade im Projekt, und in der IDE nur die Environment-Variablen.
Das ist vielleicht eine Philosophiefrage, aber so mache ich meine Projekte ziemlich autark von der benutzten IDE und Umgebung.
Damit habe ich gut Erfahrungen gemacht.

Die ganzen Fixes sind zu jedem Projekt, die Redundanz will ich reduzieren aber es kann sein das doch ein Projekt einen speziellen Fix benötigt, den ein anderes so nicht benötigt.
Das räume ich zwar ständig auf, aber die lokalen Fixes sind bei der Arbeit auch ganz praktisch,
weil ich dann immer nur im Projekt arbeite, und keinen ungeplanten Einfluss auf andere Projekte nehme.
So kann ich mehrere Projekte mit unterschiedlichen Konfigurationen nebeneinander fahren,
das wäre in der IDE mit Optionen/Pfade schwieriger zu handeln.
Die Auswirkungen der Fixes auf Mobilgeräten sind mitunter sehr mysteriös und unklar, deshalb die erhöhte Vorsicht.

Nachdem ein Fix geklärt ist kommt der in den Master, und wird er bei Bedarf in alle Projekte übernommen, oder erst Step-By-Step wenn das Verhalten noch jeweils geprüft werden muss.

Die Arbeitsweise rührt aber eher daher das ich mich eben nicht auf die IDE verlassen kann,
wie unten beschrieben.
Ich versuche Alles so einzustellen das "seltsame" Editor und Debug-Fehler gar ncht erst auftreten,
mir reichen schon die seltsamen Fehler auf den Mobilgeräten mit Permissions, Sensoren, Maps, Bluetooth, etc.

Jetzt komme ich darauf weil gerade Rx10.4 wieder etwas zickig ist, ich meine Projekte aber unbedingt bis zum 30.06. für meine Projekte lauffähig haben muss, wegen Apple's Store-Richtlinien.
Deshalb suche ich gerade ob es neue Möglichkeiten gibt die das optimieren können.
Ich sehe wieder solche "seltsamen" Effekte beim Editieren, Debuggen, etc. und habe das neue LSP und ARC im Verdacht.
Damit ich nicht nach Phantomen suche, versuche ich wenigstens die IDE-Einstellungen wasserdicht zu bekommen.

himitsu 16. Jun 2020 16:22

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Du kannst in der/den globalen Units mit
Delphi-Quellcode:
{$IFNDEF XXX}
bzw.
Delphi-Quellcode:
{$IF not Defined(XXX)}
arbeiten
und dann bei bestimmten Projekten in dessen Projekt-Optionen die Defines angeben, von dem was nicht rein soll, oder andersrum.

Alternativ geht es auch bei IncludeDateien im Quellcode.
Delphi-Quellcode:
{$DEFINE xxx}
{$INCLUDE zzz.inc}
und in der zzz.inc ein
Delphi-Quellcode:
{$IFDEF xxx}

Rolf Frei 17. Jun 2020 12:44

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Rollo62, du solltest nur Sachen in das Projeket packen, die von Standard abweichen. Packe daher alles was deinem Standard entspricht in die globalen Einstellungen und mache dann nur bei den Projekten, die von deinem Standard abweichen, Einträge in den Projektoptionen. Hälst du dich da sauber dran, wirst du keine Probleme mehr haben.

Rollo62 17. Jun 2020 13:45

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
@Rolf Frei

Ich nähere mich einer neuen Verson meistens behutsam, Bottom-Up, eher von den Demos her zu Projekten.
Leider muss ich hier in 10.4 meine Projekte ans Laufen bekommen, weil mir Kunden und Apple im Nacken sitzen, mit der .storyboard requirements.
Also muss ich leider den Top-Down Ansatz wählen, oder versuchen das in 10.3.3 reinzufrickeln.
Beides ist sub-optimal.

Ich habe jetzt das Ganze aber einigermaßen stabil bekommen, die groben Crashes scheinen wirklich von den zeitgesteuerten ListView Events zu kommen.
Ich sehe zwar nicht genau wo mir das ItemObjekt unter den Füssen weggezogen wird,
es ist aber sehr wahrscheinlich das dies irgendwo im Unterbau passiert.

Ich habe es jetzt so umgebaut das ich den Wert ignoriere, oder bei Bedarf den aktuellen Wert aus dem Listview nehme, und der Crash ist damit weg.

Das scheint für mich jetzt erstmal gelöst, ich bin noch am Testen,
aber die Baustelle hat nur Sommerpause, ich denke das brodelt später mal wieder hoch.

Zitat:

Zitat von Rolf Frei (Beitrag 1467558)
Hälst du dich da sauber dran, wirst du keine Probleme mehr haben.

Dein Wort in Gottes Ohr, aber hast Du auch Erfahrungen mit mobilen Plattformen gemacht ?
Da ist nichts mehr so wie es scheint, ich vermisse mein altes WinXP :stupid:

Rolf Frei 17. Jun 2020 15:41

AW: Unter welchen Bedingungen wird ein System-Unit Fix kompiliert und eingebunden ?
 
Zitat:

Zitat von Rollo62 (Beitrag 1467564)
Dein Wort in Gottes Ohr, aber hast Du auch Erfahrungen mit mobilen Plattformen gemacht ?
Da ist nichts mehr so wie es scheint, ich vermisse mein altes WinXP :stupid:


Nein, Gott sei Dank nicht. Habe dafür bisher keinen Bedarf gehabt und hoffe, dass ich auch nie einen haben werde. Was hier Google und Apple veranstalten ist ja echt ne Katastrophe. Da lob ich mir mein Windows, in dem ich heute noch 20 Jahre alte Anwendungen nutzen kann.


Alle Zeitangaben in WEZ +1. Es ist jetzt 12:02 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz