IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Free Pascal Discussion :

Optimisation, performance et poids d'un exécutable


Sujet :

Free Pascal

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    24
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 24
    Par défaut Optimisation, performance et poids d'un exécutable
    Bonjour à tous,

    Je reviens vers vous pour un souci "d'obésité compilatoire".
    En effet j'utilise plein de modules dans mon code, certains que j'utilise (en passant par uses), d'autres non, en fonction des programmes que je construis.
    Je me suis aperçu que, à l'inverse de ce que j'avais compris dans certains messages sur le forum, que le compilateur ne fait pas de base le ménage des modules non utilisés.

    Par exemple en laissant traîner quelques modules :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    (* Insertion des librairies MADLib Communes
    * -----------------------------------------
    *)
     
        MadLib_xml in CHEMIN_MADLIB + '/commun/madlib_xml.pas',
        MadLib_ini in CHEMIN_MADLIB + '/commun/madlib_ini.pas',
        MadLib_FileSystem in CHEMIN_MADLIB + '/commun/madlib_filesystem.pas',
        MadLib_CmdLine in CHEMIN_MADLIB + '/commun/madlib_cmdline.pas',
        MadLib_SystemEnvironment in CHEMIN_MADLIB + '/commun/madlib_systemenvironment.pas',
        MadLib_String in CHEMIN_MADLIB + '/commun/madlib_string.pas',
        MadLib_Numeric in CHEMIN_MADLIB + '/commun/madlib_numeric.pas',
        MadLib_Convert in CHEMIN_MADLIB + '/commun/madlib_convert.pas',
        MadLib_TinyLog in CHEMIN_MADLIB + '/commun/madlib_tinylog.pas',    
     
        (* MadLib_dhcpd in CHEMIN_MADLIB + '/linux/madlib_dhcpd.pas', *)
     
        (* En fonction de la plate-forme de compilation insertion des UNITES LIBRAIRIE MODULE spécifiques
        * -----------------------------------------
        *)
     
        {$IFDEF linux}
                    MadLib_dhcpd in CHEMIN_MADLIB + '/linux/madlib_dhcpd.pas',
                    MadLib_dnsmasq in CHEMIN_MADLIB + '/linux/madlib_dnsmasq.pas',
     
        {$ENDIF}
    l’exécutable fait : 1.2Mo

    En supprimant un module (XML) que je n'utilise pas dans mon code (c'est-à-dire pas de déclaration via USES), l’exécutable fait lui 800Ko.

    Bien sûr, me direz-vous, il faut enlever ce que l'on n'utilise pas, mais dans mon cas le fichier qui est utilisé est un "include" standardisé. Il n'est pas propre au programme compilé mais propre à un ensemble de sources qui utilisent les mêmes références.
    Il n'est donc pas possible de modifier ce fichier et il faut que je l'utilise puisque c'est le montage commun des modules d'un projet.

    Je me suis donc orienté vers l'optimisation avec FPC, dans le but de supprimer les modules qui ne sont pas "uses", car m'avait-on dit, que cela s'effectuait automatiquement. M'aurait-on menti ??

    Malheureusement, je ne pense pas avoir essayé les bons commutateurs, car l’exécutable fait toujours le même poids.

    Connaissez-vous donc les commutateurs qui indiquent à FPC de supprimer, par exemple, les unités non utilisées ?

    Merci d'avance de vos réponses.
    [MAD]

  2. #2
    Membre émérite

    Homme Profil pro
    Rédacteur technique (retraité)
    Inscrit en
    Octobre 2009
    Messages
    168
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 82
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Rédacteur technique (retraité)

    Informations forums :
    Inscription : Octobre 2009
    Messages : 168
    Par défaut
    Bonjour,

    Tu devrais trouver ton bonheur ici, dans le Free Pascal Programmer's Guide, Chapitre 11 Optimisations. Et peut-être plus particulièrement les sections 11.6 et 11.7 sur WPO.

    Joyeux Noël !

  3. #3
    Membre chevronné

    Homme Profil pro
    Autre
    Inscrit en
    Novembre 2015
    Messages
    145
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Autre

    Informations forums :
    Inscription : Novembre 2015
    Messages : 145
    Par défaut
    De manière générale, les procédures/fonctions (donc tout le code) non utilisées dans un module ne sont en effet pas incluses si elles ne sont pas utilisées. Donc l'affirmation concernant l'optimisation à propos du code non utilisé est vraie.

    Mais un module peut -notamment- inclure des sections "Initialization" et/ou "Finalization". Ces sections peuvent contenir du code, utiliser des classes, d'autres modules, avoir des ressources, etc ...

    Dans ce cas l'optimisation n'a pas lieu concernant tout ce qui touche à ces sections (ainsi que tous les autres modules que ces sections pourraient utiliser). Si vous n'utilisez vraiment pas ces modules, j'ai bien peur que la seule solution soit alors de ne pas les déclarer dans vos clauses 'Uses'.


    Exemple avec un petit programme Free Pascal déclarant une unité non utilisée.


    Premier cas: unité non utilisée "standard"

    Unité principale:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    program project1;
     
    uses
      UnusedUnit;
     
    begin
      WriteLn('Hello World !');
    end.
    Unité non utilisée:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    unit UnusedUnit;
     
    interface
     
    var
      MyUnusedVar: integer;
     
    procedure MyProc();
     
    implementation
     
    const
      MyString = '1234567890';
     
    procedure MyProc();
    begin
      MyUnusedVar := Length(MyString);
    end;
     
    end.
    Dans ce cas, le compilateur détecte bien que l'unité n'est pas utilisée et il n'inclut pas les éléments de cette unité:
    Hint: (11030) Start of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Hint: (11031) End of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Free Pascal Compiler version 3.0.4 [2017/12/03] for x86_64
    Copyright (c) 1993-2017 by Florian Klaempfl and others
    (1002) Target OS: Win64 for x64
    (3104) Compiling project1.lpr
    (3104) Compiling unusedunit.pas
    C:\.......\project1.lpr(4,3) Hint: (5023) Unit "UnusedUnit" not used in project1
    (9015) Linking project1.exe
    (1008) 30 lines compiled, 0.2 sec, 41504 bytes code, 1380 bytes data
    (1022) 3 hint(s) issued
    Notez bien le message du compilateur concernant la non utilisation de l'unité, et la taille du code et des données pour le programme.



    Second cas: unité non utilisée avec une clause "Initialization"

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    unit UnusedUnit;
     
    interface
     
    var
      MyUnusedVar: integer;
     
    implementation
     
    const
      MyString = '1234567890';
     
    Initialization
      MyUnusedVar := Length(MyString);
     
    end.
    Le programme n'utilise pas plus l'unité concernée mais le compilateur inclut automatiquement tout ce qui est relatif à la clause 'Initialization" (qui est déclenchée automatiquement). C'est ce qu'indique la compilation:

    Hint: (11030) Start of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Hint: (11031) End of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Free Pascal Compiler version 3.0.4 [2017/12/03] for x86_64
    Copyright (c) 1993-2017 by Florian Klaempfl and others
    (1002) Target OS: Win64 for x64
    (3104) Compiling project1.lpr
    (3104) Compiling unusedunit.pas
    (9015) Linking project1.exe
    (1008) 26 lines compiled, 0.2 sec, 41536 bytes code, 1396 bytes data
    (1022) 2 hint(s) issued
    Plus de message du compilateur, et la taille du code et des données ont été augmentées.

  4. #4
    Membre averti
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    24
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 24
    Par défaut
    Bonjour FChrisF,

    Je viens de tester l'exemple. Que l'on place de l'initialisation ou non dans l'unité, le poids fait toujours le même 176Ko.

    De mon côté je n'arrive pas à comprendre pourquoi il indique que le module n'est pas utilisé, mais qu'il recherche le fichier objet pour le lier par la suite.



    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    [0.668] erelios.pas(230,22) Hint: Variable "MyAppInfo" of a managed type does not seem to be initialized
    [0.672] erelios.pas(127,12) Hint: Local type "MyType" is not used
    [0.672] MADLib-all.inc(36,2) Hint: Unit "MadLib_xml" not used in Erelios
    [0.672] MADLib-all.inc(38,2) Hint: Unit "MadLib_FileSystem" not used in Erelios
    [0.672] MADLib-all.inc(41,5) Hint: Unit "MadLib_String" not used in Erelios
    [0.672] MADLib-all.inc(42,5) Hint: Unit "MadLib_Numeric" not used in Erelios
    [0.672] MADLib-all.inc(43,2) Hint: Unit "MadLib_Convert" not used in Erelios
    [0.672] (ERELIOS)  Unloading resource unit FPINTRES (not needed)
    [0.672] Searching file erelios.o... found
    [0.672] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl/system.o... found
    [0.680] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl/objpas.o... found
    [0.680] Searching file ./MADLib/commun/madlib_xml.o... found
    [0.680] Searching file ./MADLib/commun/madlib_ini.o... found
    [0.680] Searching file ./MADLib/commun/madlib_filesystem.o... found
    [0.680] Searching file ./MADLib/commun/madlib_cmdline.o... found
    [0.680] Searching file ./MADLib/commun/madlib_systemenvironment.o... found
    [0.680] Searching file ./MADLib/commun/madlib_string.o... found
    [0.680] Searching file ./MADLib/commun/madlib_numeric.o... found
    [0.680] Searching file ./MADLib/commun/madlib_convert.o... found
    [0.680] Searching file ./MADLib/commun/madlib_tinylog.o... found
    [0.680] Searching file ./MADLib/linux/madlib_dhcpd.o... found
    [0.680] Searching file ./MADLib/linux/madlib_dnsmasq.o... found
    [0.680] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl/sysutils.o... found
    [0.684] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl/fgl.o... found
    [0.684] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl-console/crt.o... found
    [0.684] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/fv/dialogs.o... found
    [0.688] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/fcl-xml/xmlread.o... found
    [0.688] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/fcl-xml/xmlwrite.o... found
    [0.688] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/fcl-xml/xmlutils.o... found
    [0.688] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/fcl-xml/xmlstreaming.o... found
    [0.688] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/fcl-xml/dom.o... found
    Quand je supprime les fichiers qu'il trouve et que je relance la compilation ...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    Warning: Object madlib_xml.o not found, Linking may fail !
    Warning: Object madlib_ini.o not found, Linking may fail !
    Warning: Object madlib_filesystem.o not found, Linking may fail !
    Warning: Object madlib_cmdline.o not found, Linking may fail !
    Warning: Object madlib_systemenvironment.o not found, Linking may fail !
    Warning: Object madlib_string.o not found, Linking may fail !
    Warning: Object madlib_numeric.o not found, Linking may fail !
    Warning: Object madlib_convert.o not found, Linking may fail !
    Warning: Object madlib_tinylog.o not found, Linking may fail !
    Linking erelios
    /usr/bin/ld.bfd*: avertissement*: link.res contient des sections de sortie; avez-vous oublié -T?
    /usr/bin/ld.bfd*: ne peut trouver madlib_xml.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_ini.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_filesystem.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_cmdline.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_systemenvironment.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_string.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_numeric.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_convert.o
    /usr/bin/ld.bfd*: ne peut trouver madlib_tinylog.o
    Error: Error while linking
    Fatal: There were 1 errors compiling module, stopping

  5. #5
    Membre chevronné

    Homme Profil pro
    Autre
    Inscrit en
    Novembre 2015
    Messages
    145
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Autre

    Informations forums :
    Inscription : Novembre 2015
    Messages : 145
    Par défaut
    Si vous parlez de mon petit exemple précédent (même taille d'exécutable de 176 Ko), c'est tout à fait normal: il n'y a en effet pas assez de code et/ou de données concernés pour que cela impacte la taille de l'exécutable final (32 octets de code et 16 octets de données en 64 bits seulement !).

    Il faut bien sûr projeter cet exemple dans le cas ou beaucoup de code, de données, de ressources, etc... sont utilisés; et je ne parle pas du code présent uniquement dans les sections Initialization/Finalization du module, mais de aussi tout le code qu'il peut appeler dans d'autre modules, ainsi que des éventuelles propres sections Initialization/Finalization des "sous-modules" utilisés par le module concerné (et ainsi de suite en cascade).

    Voici donc un autre petit exemple, qui induit une -légère- différence de taille dans l'exécutable cette fois: même unité principale mais unité non utilisée suivante:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    unit UnusedUnit;
     
    {$mode objfpc}{$H+}
     
    interface
     
    uses
      PasZlib;
     
    function TestZlib(): boolean;
     
    implementation
     
    function TestZlib(): boolean;
    var Data1: array [0..pred(256)] of byte;
    var Data2: array [0..pred(1024)] of byte;
    var DataLen1, DataLen2: cardinal;
    begin
      result := false;
      Data1[0] := 0; Data2[0] := 0;   // avoid hint
      FillChar(Data1, SizeOf(Data1), $A5);
      FillChar(Data2, SizeOf(Data2), 0);
      DataLen1 := SizeOf(Data1);
      DataLen2 := SizeOf(Data2);
      if compress(@Data2[0], DataLen2, @Data1[0], DataLen1) = Z_OK then
        begin
          FillChar(Data1, SizeOf(Data1), 0);
          if uncompress(@Data1[0], DataLen1, @Data2[0], DataLen2) = Z_OK then
            if (Data1[0] = $A5) and (Data1[pred(256)] = $A5) then
              result := true;
        end;
    end;
     
    Initialization
      TestZlib();
     
    end.
    Avec la section Initialization :
    Hint: (11030) Start of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Hint: (11031) End of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Free Pascal Compiler version 3.0.4 [2017/12/03] for x86_64
    Copyright (c) 1993-2017 by Florian Klaempfl and others
    (1002) Target OS: Win64 for x64
    (3104) Compiling project1.lpr
    (3104) Compiling unusedunit.pas
    (9015) Linking project1.exe
    (1008) 45 lines compiled, 0.2 sec, 74224 bytes code, 5076 bytes data
    (1022) 2 hint(s) issued
    Soit au total pour moi 152 Ko pour l'exécutable (Windows FPC 64 bits 3.0.4, O1, avec debug).


    Même chose, mais en commentant cette fois la section Initialization:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    //Initialization
    //  TestZlib();
    Hint: (11030) Start of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Hint: (11031) End of reading config file C:\lazarus\fpc\3.0.4\bin\x86_64-win64\fpc.cfg
    Free Pascal Compiler version 3.0.4 [2017/12/03] for x86_64
    Copyright (c) 1993-2017 by Florian Klaempfl and others
    (1002) Target OS: Win64 for x64
    (3104) Compiling project1.lpr
    (3104) Compiling unusedunit.pas
    C:\.....\project1.lpr(4,3) Hint: (5023) Unit "UnusedUnit" not used in project1
    (9015) Linking project1.exe
    (1008) 45 lines compiled, 0.2 sec, 41600 bytes code, 1492 bytes data
    (1022) 3 hint(s) issued
    Soit au total 104 Ko (Windows FPC 64 bits 3.0.4, O1, avec debug).



    Concernant la seconde partie de votre message, c'est difficile à dire sans avoir le code sous les yeux. Ceci étant je note que le compilateur indique 5 unités "MadLib_..." non utilisées, alors que vous en supprimez ensuite 9: il y en aurait (conditionnel) donc 4 de nécessaires ...

  6. #6
    Membre averti
    Profil pro
    Inscrit en
    Octobre 2009
    Messages
    24
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Octobre 2009
    Messages : 24
    Par défaut
    Oui tout à fait j'ai fait exprès de supprimer 9 objets, afin de savoir s'il faisait le tri. Pour l'instant je peux m'apercevoir, qu'il ne fait pas le tri, entre ceux dont j'ai besoin ou non.
    Il prend tout sans se soucier de l'étape effectuée plus haut où il indique que n'ai pas besoin du XML par exemple.

    Bien sûr, en supprimant les PPU il reconstruit l’ensemble. Mais avec les modules dont il n'a pas besoin.


    [0.730] Stack frame is omitted
    [0.730] Stack frame is omitted
    [0.730] erelios.pas(127,12) Hint: Local type "MyType" is not used
    [0.730] MADLib-all.inc(36,2) Hint: Unit "MadLib_xml" not used in Erelios
    [0.730] MADLib-all.inc(38,2) Hint: Unit "MadLib_FileSystem" not used in Erelios
    [0.730] MADLib-all.inc(41,5) Hint: Unit "MadLib_String" not used in Erelios
    [0.730] MADLib-all.inc(42,5) Hint: Unit "MadLib_Numeric" not used in Erelios
    [0.730] MADLib-all.inc(43,2) Hint: Unit "MadLib_Convert" not used in Erelios
    [0.730] (ERELIOS) Unloading resource unit FPINTRES (not needed)
    [0.730] Assembling erelios
    [0.730] Searching file /usr/lib/fpc/3.0.0/bin/x86_64-linux/as... not found
    [0.730] Searching file /usr/lib/fpc/3.0.0/bin/x86_64-linux/AS... not found
    [0.730] Searching file /usr/lib/fpc/3.0.0/as... not found
    [0.730] Searching file /usr/lib/fpc/3.0.0/AS... not found
    [0.730] Searching file /usr/local/bin/as... not found
    [0.730] Searching file /usr/local/bin/AS... not found
    [0.730] Searching file /usr/bin/as... found
    [0.730] Using assembler: /usr/bin/as
    [0.730] Executing "/usr/bin/as" with command line "--64 -o erelios.o erelios.s"
    [0.750] Searching file erelios.o... found
    [0.750] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl/system.o... found
    [0.758] Searching file /usr/lib/fpc/3.0.0/units/x86_64-linux/rtl/objpas.o... found
    [0.758] Searching file ./MADLib/commun/madlib_xml.o... found
    [0.758] Searching file ./MADLib/commun/madlib_ini.o... found
    [0.758] Searching file ./MADLib/commun/madlib_filesystem.o... found
    [0.758] Searching file ./MADLib/commun/madlib_cmdline.o... found
    [0.758] Searching file ./MADLib/commun/madlib_systemenvironment.o... found
    [0.758] Searching file ./MADLib/commun/madlib_string.o... found
    [0.758] Searching file ./MADLib/commun/madlib_numeric.o... found
    [0.758] Searching file ./MADLib/commun/madlib_convert.o... found
    [0.758] Searching file ./MADLib/commun/madlib_tinylog.o... found
    [0.758] Searching file ./MADLib/linux/madlib_dhcpd.o... found
    [0.758] Searching file ./MADLib/linux/madlib_dnsmasq.o... found

Discussions similaires

  1. Optimisation performance MYSQL
    Par adapt dans le forum Requêtes
    Réponses: 1
    Dernier message: 29/09/2009, 15h10
  2. Optimisation requête pour cause de Maximum execution time
    Par cans38 dans le forum Langage SQL
    Réponses: 2
    Dernier message: 01/09/2008, 15h36
  3. Optimisation performance accès BD pour appli Web
    Par killysui dans le forum ASP.NET
    Réponses: 10
    Dernier message: 23/06/2008, 14h23
  4. Réponses: 3
    Dernier message: 05/04/2006, 15h13
  5. [Access] Optimisation performance requête - Index
    Par fdraven dans le forum Access
    Réponses: 11
    Dernier message: 12/08/2005, 14h30

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo