La pregunta que ha vinculado hace referencia a la funcionalidad "Vincular binario con bibliotecas", que es algo diferente de un binario incrustado.
"Enlace binario con bibliotecas" significa lo que esperaría con respecto al enlace: Independientemente de si el binario es una biblioteca estática, una biblioteca dinámica o un marco, estará vinculado a su código de objeto en el momento del enlace después de la compilación.
Cuando piensa en la vinculación con una biblioteca estática, lo que sucede es bastante claro: el vinculador copia el código de la biblioteca (por ejemplo libFoo.a
) en su binario de salida. Su archivo de salida aumenta de tamaño pero no necesita resolver ninguna dependencia externa en tiempo de ejecución. Todo lo que su programa necesita para ejecutarse (con respecto a la biblioteca estática) está presente después de su creación.
Con una biblioteca dinámica (.dylib, o marco proporcionado por el sistema), la expectativa es que la biblioteca con la que se está vinculando estará presente en algún lugar de la ruta del cargador de la biblioteca dinámica del sistema cuando ejecute su programa. De esta manera no tiene la sobrecarga de copiar todas las bibliotecas externas de terceros en su binario, y todos los diferentes programas en una computadora que también se vinculan a esa biblioteca podrán encontrarla, lo que ahorra un mínimo espacio en disco, pero también potencialmente espacio de memoria, dependiendo de cómo y dónde el sistema almacena en caché las bibliotecas.
Un marco es muy parecido a una biblioteca dinámica, pero puede contener recursos en su estructura de directorios (imágenes, audio, otros marcos, etc.). En este caso, una simple biblioteca estática o un archivo .dylib no lo cortará, por lo que es posible que deba vincular a un marco solo para que pueda encontrar lo que necesita para ejecutarse correctamente.
Cuando se vincula a un marco de terceros (digamos algo que descargó de github y creó usted mismo), es posible que no esté presente en el sistema en el que desea ejecutar. En este caso, no solo se vincularía al marco, sino que también lo incrustaría dentro del paquete de la aplicación utilizando la fase "Copiar marcos". Cuando se ejecuta su programa, el runtime-linker (también conocido como el resolutor) buscará dentro de su paquete además de la ruta del cargador del sistema, encontrará el marco incrustado y lo vinculará para que su aplicación tenga el código que necesita para ejecutarse.
Finalmente, lo que es propiamente un "binario incrustado" es un ejecutable que ambos incrustan en su paquete de aplicaciones a través de una Fase de Copiar Archivos, y que usted mismo ejecuta, tal vez con una llamada popen()
o similar. El programa puede llamar al binario incrustado, pero no está vinculado con él. Es una entidad totalmente externa (como los programas en el /bin
directorio).
En la práctica, para bibliotecas y marcos proporcionados por el sistema, se vinculará con ellos y eso es todo lo que necesita hacer.
Si necesita vincular una biblioteca que creó que no necesita ningún recurso incrustado (es decir, no requiere que exista un marco), puede simplemente vincular con una biblioteca estática. Si descubre que tiene varios módulos en su programa que desean usar el mismo código de biblioteca, luego convertirlo en un marco o biblioteca dinámica y vincularlo puede ahorrar espacio y puede ser conveniente (particularmente si el uso de memoria es una preocupación).
Finalmente, los marcos pueden incluir no solo recursos, sino también encabezados y / o archivos de licencia. El uso de un marco para transmitir estos archivos es en realidad un mecanismo de distribución conveniente, por lo que a menudo es posible que desee incorporar un marco solo para que estas cosas puedan etiquetarse junto con su binario (es decir, los requisitos de licencia pueden hacer que esto sea obligatorio).
--- EDITAR ---
Adam Johns publicó la siguiente pregunta como comentario:
Esta es una respuesta genial. Sin embargo, hay algo en lo que todavía estoy un poco confundido. ¿Qué significa ejecutar el binario usted mismo? ¿Te refieres a simplemente usar el código del marco incrustado? Sé que mencionaste popen (), pero ¿estás diciendo que mi aplicación está llamando popen ()? Realmente no sé lo que eso significa.
Estoy diciendo que un binario incrustado es solo otro archivo de recursos en su paquete, como un archivo de audio o una imagen, aunque el archivo es en cambio una herramienta de línea de comandos ejecutable. La popen()
función ( man popen
desde su terminal para leer más al respecto) le permite ejecutar programas arbitrarios desde otro programa en ejecución. La system()
función es otra forma. Hay otros, y daré un ejemplo histórico aquí que puede aclarar un poco más el uso de un binario incrustado:
Como probablemente sepa, cuando inicia una aplicación en Mac OS X, se inicia con una identificación de usuario del usuario actual. En las instalaciones más comunes, ese es el usuario predeterminado de usuario en el escritorio admin
, a quien se le asigna la identificación de usuario 501
.
En los sistemas operativos basados en Unix, solo el root
usuario (ID de usuario 0
) tiene acceso completo a todo el sistema de archivos. A veces sucede que un programa instalador lanzado por el usuario de Desktop necesita instalar archivos en un directorio privilegiado (controladores, por ejemplo). En este caso, el programa de aplicación necesita escalar sus privilegios al root
usuario para que pueda escribir en estos directorios restringidos.
Para facilitar esto en los sistemas operativos a través de OS X 10.7, Apple proporcionó en su API de servicios de autorización la función AuthorizationExecuteWithPrivileges () (ahora está en desuso, pero sigue siendo un ejemplo útil).
AuthorizationExecuteWithPrivileges()
tomó como argumento una ruta a una herramienta de línea de comandos para ejecutar como root
. La herramienta de línea de comandos era un script de shell ejecutable o un binario compilado que escribiste para ejecutar tu lógica de instalación. Esta herramienta se instaló dentro de su paquete de aplicaciones como cualquier otro archivo de recursos.
Cuando se le llama, el sistema operativo muestra un cuadro de diálogo de autorización que solicita la contraseña del usuario (¡ya lo ha visto antes!) Y, cuando se ingresa, ejecuta el programa como root
en nombre de su aplicación. Este proceso es similar a solo ejecutar un programa popen()
contigo mismo, aunque popen()
solo no te da el beneficio de la escalada de privilegios.