-I dir vs. -isystem dir

Lesezeit: 4 Minuten

Wenn ich Verzeichnisse einbeziehen möchte, die nach Header-Dateien durchsucht werden sollen, was ist der bevorzugte Weg und warum?

  • Einschließen oder Ausschließen der Host-Standard-C-Bibliothek?

    – Tim Post

    5. April 2010 um 16:42 Uhr

  • Weder das eine, noch das andere. Habe gerade im GCC-Handbuch über Vorverarbeitungsoptionen gelesen und bin über diese beiden gestolpert.

    – Helfermethode

    6. April 2010 um 8:54 Uhr

  • Eine große Verwendung von -isystem gegenüber -I besteht darin, dass Warnungen in -isystem ignoriert werden. Dies ist nützlich, wenn Sie mit -Wall -Werror kompilieren möchten, aber keine Fehler in den -isystem-Verzeichnissen erhalten möchten.

    – Eja

    17. Januar 2021 um 16:35 Uhr

Eine Möglichkeit, dies anzuzeigen, besteht darin, Header zu verwenden, mit denen Sie steuern -I und diejenigen, mit denen Sie es nicht tun (System, Bibliotheken von Drittanbietern). -isystem. Der praktische Unterschied besteht darin, dass Warnungen aktiviert werden, aus denen Warnungen stammen -isystem Kopfzeilen werden unterdrückt.

Benutzeravatar von Justin Ethier
Justin Ether

Von dem gcc-Dokumentation für -I:

Fügen Sie das Verzeichnis dir am Kopf der Liste der Verzeichnisse hinzu, die nach Header-Dateien durchsucht werden sollen. Dies kann verwendet werden, um eine Systemheaderdatei zu überschreiben und Ihre eigene Version zu ersetzen, da diese Verzeichnisse vor den Systemheaderdateiverzeichnissen durchsucht werden. Sie sollten diese Option jedoch nicht verwenden, um Verzeichnisse hinzuzufügen, die vom Hersteller bereitgestellte System-Header-Dateien enthalten (verwenden Sie dafür -isystem). Wenn Sie mehr als eine Option -I verwenden, werden die Verzeichnisse von links nach rechts gescannt; die Standardsystemverzeichnisse kommen danach.

Wenn ein standardmäßiges System-Include-Verzeichnis oder ein mit -isystem angegebenes Verzeichnis auch mit -I angegeben wird, wird die Option -I ignoriert. Das Verzeichnis wird weiterhin durchsucht, jedoch als Systemverzeichnis an seiner normalen Position in der System-Include-Kette. Dadurch soll sichergestellt werden, dass das Verfahren von GCC zum Beheben fehlerhafter Systemheader und die Reihenfolge für die include_next-Direktive nicht versehentlich geändert werden. Wenn Sie die Suchreihenfolge für Systemverzeichnisse wirklich ändern müssen, verwenden Sie die Optionen -nostdinc und/oder -isystem.

So -I ist wahrscheinlich die bevorzugte Option, um den Speicherort Ihrer Header-Dateien anzugeben, mit Ausnahme von Sonderfällen, wie z. B. vom Anbieter bereitgestellte System-Header.

Sie sollten -I verwenden, um die Position Ihrer Header anzugeben.

Die Dateien, die Sie mit -isystem angeben, werden nach der Verarbeitung von -I durchsucht und erhalten eine Sonderbehandlung durch gcc (wie Standard-System-Header).

Hier ist also der Unterschied, den ich durch einige Experimente gefunden habe. Stellen Sie sich folgendes Setup vor:

my_std_lib/stdio.h

#ifndef _CUSTOM_STDIO_H

void test() {}

#endif

#include_next <stdio.h>
#include_next <custom.h>

my_user_lib/custom.h

#ifndef _CUSTOM_HEADER_H

void custom_func() {}

#endif

main.cpp

#include "stdio.h"

int main() {
  test();
  custom_func();
  printf("Hello world!");
  return 0;
}

Wenn Sie mit kompilieren
g++ -isystem my_std_lib -isystem my_user_lib main.cpp alles wird gut funktionieren.

Jedoch, g++ -isystem my_std_lib -I my_user_lib main.cpp führt zu einem Fehler

In file included from main.cpp:1:
my_std_lib/stdio.h:10:15: fatal error: 'custom.h' file not found
#include_next <custom.h>
              ^~~~~~~~~~
1 error generated.

Also, was ist los?

Nach meinem Verständnis, wenn ich schreibe #include "stdio.h"beginnt GCC, die Liste der verfügbaren Header-Dateien zu durchlaufen, bis es sie findet my_std_lib/stdio.h. Richtlinie #include_next <custom.h> am Ende dieser Datei weist den Compiler an, nach a zu suchen custom.h durch Durchlaufen von include-Verzeichnissen von its aktuell Stelle weiter.

Wenn ich hinzufüge my_user_lib zur Liste der Verzeichnisse mit -I Flagge, so scheint es Vor alle Systemverzeichnisse in der Verzeichnisliste. Daher taucht es in der Liste davor auf my_std_lib Verzeichnis und die #include_next scheitert.

Dasselbe würde passieren, wenn ich mit kompilieren würde g++ -isystem my_user_lib -isystem my_std_lib main.cpp. Anscheinend werden Verzeichnisse in der gleichen Reihenfolge zur Liste hinzugefügt, in der die Flags angegeben werden, also noch einmal, my_user_lib wird vorher kommen my_std_lib.

Also kurz gesagt, -I und -isystem unterscheiden sich dadurch, dass sie ihr Ziel zur Liste der Include-Verzeichnisse hinzufügen.

Wenn Sie einen Header „Myheader.h“ mit -I einfügen, generiert der Compiler eine Suchreihenfolge: „Myheader.h“ , „system/headers“. Wenn also etwas nicht in “MyHeader.h” zu finden ist, greifen Sie auf “system/headers” zurück. Wenn Sie jedoch -isystem verwenden, sagen Sie im Grunde, dass Sie “system/headers” durch das ersetzen, was ich Ihnen gebe. Ein Rückgriff auf “System/Header” entfällt also.

1394920cookie-check-I dir vs. -isystem dir

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy