Que signifie -fPIC lors de la création d'une bibliothèque partagée?

109

Je sais que l' -fPICoption « » a quelque chose à voir avec la résolution des adresses et l'indépendance entre les modules individuels, mais je ne suis pas sûr de ce que cela signifie vraiment. Peux-tu expliquer?

ks1322
la source
1
Également au cas où vous voudriez savoir plus en détail, il y a un excellent article ici ( akkadia.org/drepper/dsohowto.pdf )
MJ

Réponses:

61

PIC signifie Position Independent Code

et citer man gcc:

S'il est pris en charge pour la machine cible, émettez un code indépendant de la position, adapté à la liaison dynamique et évitant toute limite de taille de la table de décalage globale. Cette option fait une différence sur le m68k, le PowerPC et le SPARC. Le code indépendant de la position nécessite un support spécial et ne fonctionne donc que sur certaines machines.

utilisez ceci lors de la construction d'objets partagés (* .so) sur les architectures mentionnées.

sean riley
la source
1
f ne veut rien dire, c'est juste une partie du nom de l'option.
Zifre
17
Il y a une différence entre fpic et fPIC. Ils font tous les deux la même chose mais fpic utilise un décalage relatif plus court s'il est disponible. Ainsi, la compilation avec fpic peut potentiellement produire des fichiers plus petits. Malheureusement, cela ne fonctionne pas toujours comme prévu, utilisez donc fPIC. Notez également que tous les processeurs ne prennent pas en charge les décalages les plus courts, donc cela peut ne pas faire de différence.
Martin York
2
Le 'f' est une gueule de bois de la façon dont gcc traitait les arguments de ligne de commande (c'était il y a quelques années et ils ont changé cette partie du code que je n'ai pas regardée récemment). Mais à l'époque, seules certaines lettres ou combinaisons étaient autorisées dans des conditions différentes (il y avait un langage très complexe pour définir les arguments de ligne de commande) en conséquence, le «f» était utilisé pour le rendre facile à définir comme argument de ligne de commande.
Martin York
2
Que se passera-t-il si l'on construit un * .so sans fPIC?
Isa A
2
@IsaA Je compilais une fonction mysql c-api à partir de la source aujourd'hui et elle ne serait pas /usr/bin/ld: /tmp/cc7hXILq.o: relocation R_X86_64_32 against `.rodata' can not be used when making a shared object; recompile with -fPICcompilée , j'ai donc ajouté fPIC et il a été construit.
chiliNUT
32

Le fest le préfixe gcc pour les options qui "contrôlent les conventions d'interface utilisées dans la génération de code"

L' PICabréviation de "Position Independent Code", c'est une spécialisation du fpicfor m68K et SPARC.

Edit: Après avoir lu la page 11 du document référencé par 0x6adb015 , et le commentaire de coryan, j'ai apporté quelques modifications:

Cette option n'a de sens que pour les bibliothèques partagées et vous indiquez au système d'exploitation que vous utilisez une table de décalage globale, GOT. Cela signifie que toutes vos références d'adresse sont relatives au GOT et que le code peut être partagé entre plusieurs processus.

Sinon, sans cette option, le chargeur devrait modifier lui-même tous les décalages.

Inutile de dire que nous utilisons presque toujours -fpic / PIC.

Mark Beckwith
la source
1
Je pensais que le système d'exploitation était libre de charger la bibliothèque dans n'importe quelle adresse virtuelle, mais sans pic / PIC, le chargeur doit modifier le code et ajuster tous les sauts absolus + indirections aux emplacements réels des routines / bibliothèques. Avec pic / PIC, le code n'est pas modifié et est donc réellement partagé entre plusieurs processus.
coryan
Plusieurs processus sont en grande partie coïncidents - leur point clé est que le code peut être chargé à n'importe quelle adresse virtuelle avec un minimum absolu de corrections d'adresse.
Jonathan Leffler
16

man gcc dit:

-fpic
  Générer un code indépendant de la position (PIC) adapté à une utilisation dans un
  bibliothèque, si elle est prise en charge pour la machine cible. Un tel code accède à tous
  adresses constantes via une table de décalage globale (GOT). La dynamique
  loader résout les entrées GOT au démarrage du programme (le
  loader ne fait pas partie de GCC; il fait partie du système d'exploitation). Si
  la taille GOT de l'exécutable lié dépasse une valeur spécifique à la machine
  taille maximale, vous obtenez un message d'erreur de l'éditeur de liens indiquant
  que -fpic ne fonctionne pas; dans ce cas, recompilez avec -fPIC à la place.
  (Ces maximums sont de 8k sur le SPARC et de 32k sur le m68k et le RS / 6000.
  Le 386 n'a pas une telle limite.)

  Le code indépendant de la position nécessite un support spécial, et donc
  ne fonctionne que sur certaines machines. Pour le 386, GCC prend en charge PIC pour
  System V mais pas pour le Sun 386i. Code généré pour le
  IBM RS / 6000 est toujours indépendant de la position.

-fPIC
  Si pris en charge pour la machine cible, émettez un code indépendant de la position,
  adapté à la liaison dynamique et en évitant toute limite de taille
  la table de décalage global. Cette option fait la différence sur le m68k
  et le SPARC.

  Le code indépendant de la position nécessite un support spécial, et donc
  ne fonctionne que sur certaines machines.
Nikolai Fetissov
la source