2011-01-05 22 views
56

Acabo de descubrir que gcc necesita la bandera -lm para compilar un programa que refiere una función de la biblioteca matemática. Me pregunto por qué no se necesita un marcador de enlace explícito al compilar programas que contienen otras bibliotecas, como la biblioteca de tiempo. Si escribo un programa donde se llama a la función time(), se compilará sin problemas, incluso sin opciones de vinculación. Pero un programa con la biblioteca matemática involucrada simplemente no funcionará sin la bandera -lm.gcc: ¿por qué la bandera -lm es necesaria para vincular la biblioteca matemática?

¿Puede alguien explicar el motivo de este comportamiento? Gracias por tu tiempo.

+4

Razones históricas raras, pero principalmente porque así es: http://stackoverflow.com/questions/1033898/why-do-you-have-to-link-the-math-library-in-c – birryree

Respuesta

32

Debido time() y algunas otras funciones son builtin definido en la biblioteca C (libc) en sí y GCC siempre enlaces a LIBC a menos que utilice la opción de compilación -ffreestanding. Sin embargo, las funciones matemáticas viven en libm, que no está implícitamente vinculado por gcc.

+4

Activado LLVM gcc No tengo que agregar -lm. ¿Por qué es esto? –

55

Debido a la práctica histórica ridícula que nadie está dispuesto a arreglar. La consolidación de todas las funciones requeridas por C y POSIX en un solo archivo de biblioteca no solo evitaría que esta pregunta se repitiera una y otra vez, sino que también ahorraría una cantidad significativa de tiempo y memoria cuando se vinculan dinámicamente, ya que cada archivo .so requiere el sistema de archivos operaciones para localizar y encontrar, y un par de páginas para sus variables estáticas, traslados, etc.

una implementación que todas las funciones están en una biblioteca y el -lm, -lpthread, -lrt, etc. opciones son todos los no-ops (o el enlace para vaciar los archivos .a) es perfectamente compatible con POSIX y sin duda es preferible.

Nota: Estoy hablando de POSIX porque C no especifica nada acerca de cómo se invoca el compilador. Por lo tanto, puede tratar gcc -std=c99 -lm como la forma específica de implementación en que debe invocarse el compilador para el comportamiento conforme.

+8

+1 para señalar que POSIX no requiere que existan bibliotecas libm, libc y librt separadas. Como ejemplo, en Mac OS todo está ubicado en un solo libSystem (que también incluye libdbm, libdl, libgcc_s, libinfo, libm, libpoll, libproc y librpcsvc). –

+3

-1 para especular sobre el efecto de la búsqueda de bibliotecas en el rendimiento sin hacer una copia de seguridad con un enlace o números. "Perfil. No especule" –

+7

Esto no es especulación. No tengo ningún artículo publicado, pero he hecho todas las mediciones yo mismo y la diferencia es enorme. Simplemente use 'strace' con una de las opciones de tiempo para ver cuánto tiempo de inicio se usa en enlaces dinámicos, o compare ejecutando'./Configure' en un sistema donde todas las utilidades estándar están vinculadas estáticamente contra una donde son dinámicas -vinculado. Incluso los principales desarrolladores de aplicaciones de escritorio y los integradores de sistemas son conscientes del costo de los enlaces dinámicos; es por eso que existen cosas como Prelink. Estoy seguro de que puede encontrar puntos de referencia en algunos de esos documentos. –

Cuestiones relacionadas