¿Dónde busca gcc los archivos de encabezado C y C ++?

186

En un sistema Unix, ¿dónde busca gcc los archivos de encabezado?

Pasé un poco de tiempo esta mañana buscando algunos archivos de encabezado del sistema, así que pensé que sería una buena información tener aquí.

Bill el lagarto
fuente

Respuestas:

227
`gcc -print-prog-name=cc1plus` -v

Este comando le pregunta a gcc qué preprocesador de C ++ está usando y luego le pregunta a ese preprocesador dónde busca incluir.

Obtendrá una respuesta confiable para su configuración específica.

Del mismo modo, para el preprocesador C :

`gcc -print-prog-name=cpp` -v
Drew Dormann
fuente
2
¿Qué significan los `s? Me resulta difícil buscar esto.
mijiturka 23/03/2016
55
Supongo que el preprocesador C es en cpplugar de cc1? En mi debian jessie $(gcc -print-prog-name=cpp) -v(correctamente) da un camino más, que es/usr/include/x86_64-linux-gnu
wlnirvana
3
Si desea que no se cuelgue esperando la entrada, redirija la entrada desde /dev/null, así `gcc -print-prog-name=cc1` -v < /dev/null.
Steve Jorgensen
@SteveJorgensen sip! O presione Ctrl+ D, que envía "fin de archivo" en Unix-talk.
Drew Dormann el
40

Además, gcc buscará en los directorios especificados después de la -Iopción.


robert
fuente
44
@totaam: ¡Comprueba tu fuente! Esta respuesta usa "-I" ("ojo" en mayúscula) no "-l" (minúscula "ell").
3
-I es para <anglebracketed.h> mientras que -iquote es para "quotedfiles.h"
jcomeau_ictx
28

Puede crear un archivo que intente incluir un encabezado falso del sistema. Si ejecuta gcc en modo detallado en una fuente de este tipo, enumerará todas las ubicaciones de inclusión del sistema a medida que busca el encabezado falso.

$ echo "#include <bogus.h>" > t.c; gcc -v t.c; rm t.c

[..]

#include "..." search starts here:
#include <...> search starts here:
 /usr/local/include
 /usr/lib/gcc/i686-apple-darwin9/4.0.1/include
 /usr/include
 /System/Library/Frameworks (framework directory)
 /Library/Frameworks (framework directory)
End of search list.

[..]

t.c:1:32: error: bogus.h: No such file or directory
diciu
fuente
3
Creo que esto sería más útil si dijeras "usa la opción -v".
Jay Conrod
Bueno, si usa "-v" sin un archivo C que incluya un encabezado de sistema inexistente, no hará que gcc recorra todas las rutas de inclusión. La clave de mi respuesta es falsa .h aparece como un encabezado del sistema.
diciu
@ Jay: tienes razón, era demasiado vago: he explicado lo que estaba haciendo en el script de shell.
diciu
9
sin archivos temporales:echo "#include <bogus.h>" | gcc -v -x c -
thejoshwolfe
2
gcc -v -E - < /dev/nullo cpp -v < /dev/nullson suficientes Solo tiene que ejecutar el preprocesador , no importa qué entrada vea. (Las rutas de búsqueda se imprimen durante el inicio, incluso antes de que vea su entrada).
zwol
17

La Sección de CPP del Manual de GCC indica que los archivos de encabezado pueden ubicarse en los siguientes directorios:

GCC busca en varios lugares diferentes encabezados. En un sistema Unix normal, si no le indica lo contrario, buscará los encabezados solicitados con #include en:

 /usr/local/include
 libdir/gcc/target/version/include
 /usr/target/include
 /usr/include

Para los programas de C ++, también se verá en / usr / include / g ++ - v3, primero.

Bill el lagarto
fuente
Eso está bien para su versión actual de gcc. Los directorios reales en los que se ve dependen de las opciones especificadas cuando se creó gcc. Vea la respuesta de Shmoopty para una mejor solución.
Martin York
PD: Mis archivos de encabezado C ++ están en: /usr/include/c++/4.0.0
Martin York
3
@ Martin: Eres de la vieja escuela. Los míos están en /usr/include/c++/4.2 :)
Bill the Lizard
10

Para que GCC imprima el conjunto completo de directorios donde buscará encabezados del sistema, invoque de esta manera:

$ LC_ALL=C gcc -v -E -xc - < /dev/null 2>&1 | 
  LC_ALL=C sed -ne '/starts here/,/End of/p'

que producirá la salida del formulario

#include "..." search starts here:
#include <...> search starts here:
 /usr/lib/gcc/x86_64-linux-gnu/5/include
 /usr/local/include
 /usr/lib/gcc/x86_64-linux-gnu/5/include-fixed
 /usr/include/x86_64-linux-gnu
 /usr/include
End of search list.

Si tiene -Iopciones de familia en la línea de comando, afectarán lo que se imprime.

(El sedcomando es deshacerse de todos los demás archivos basura que imprime esta invocación, y LC_ALL=Ces asegurarse de que el sedcomando funcione: las frases "comienza aquí" y "Fin de la lista de búsqueda" se traducen IIRC).

zwol
fuente
9
g++ -print-search-dirs
gcc -print-search-dirs
usuario292283
fuente
3
Estos comandos imprimen las rutas de búsqueda predeterminadas para bibliotecas de enlaces y componentes internos del compilador; no te dicen nada sobre los archivos de encabezado.
zwol
6

El comando puede verificar el conjunto de rutas donde el compilador busca los archivos de encabezado: -

cpp -v

Si declara #include "" , el compilador primero busca en el directorio actual del archivo fuente y, si no lo encuentra, continúa buscando en los directorios recuperados anteriormente.

Si declara #include <> , el compilador busca directamente en los directorios obtenidos del comando anterior.

Fuente: http://commandlinefanatic.com/cgi-bin/showarticle.cgi?article=art026

Suhas Chikkanna
fuente
1

Uno podría ver la ruta de inclusión (adicional) para un programa C desde bash al verificar lo siguiente:

echo $C_INCLUDE_PATH

Si está vacío, podría modificarse para agregar ubicaciones de inclusión predeterminadas, de la siguiente manera:

export C_INCLUDE_PATH=$C_INCLUDE_PATH:/usr/include
usuario2844647
fuente
1

Estos son los directorios en los que gcc busca de manera predeterminada los archivos de encabezado especificados (dado que los archivos de encabezado están incluidos en los galones <>); 1. / usr / local / include / --utilizado para archivos de encabezado de terceros. 2. / usr / include /: se utiliza para los archivos de encabezado del sistema.

Si decide colocar su archivo de encabezado personalizado en un lugar que no sea los directorios mencionados anteriormente, puede incluirlos de la siguiente manera: 1. usando comillas ("./custom_header_files/foo.h") con la ruta de los archivos, en lugar de galones en la declaración de inclusión. 2. usando el modificador -I al compilar el código. gcc -I / home / user / custom_headers / -c foo.c -p foo.o Básicamente, el modificador -I le dice al compilador que primero busque en el directorio especificado con el modificador -I (antes de verificar los directorios estándar). usando el modificador -I, los archivos de encabezado se pueden incluir usando galones.

akhil tiwari
fuente