Lanzamento da biblioteca C estándar Cosmopolitan 2.0, desenvolvida para ficheiros executables portátiles

Publicouse o lanzamento do proxecto Cosmopolitan 2.0, que desenvolve a biblioteca C estándar e un formato de ficheiro executable universal que se pode utilizar para distribuír programas para diferentes sistemas operativos sen o uso de intérpretes e máquinas virtuais. O resultado obtido mediante a compilación en GCC e Clang compílase nun ficheiro executable universal ligado estáticamente que se pode executar en calquera distribución de Linux, macOS, Windows, FreeBSD, OpenBSD, NetBSD, e mesmo chamado desde a BIOS. O código do proxecto distribúese baixo a licenza ISC (unha versión simplificada de MIT/BSD).

O contedor para xerar ficheiros executables universais baséase na combinación de segmentos e cabeceiras específicos de diferentes sistemas operativos (PE, ELF, MACHO, OPENBSD) nun ficheiro, combinando varios formatos diferentes utilizados en Unix, Windows e macOS. Para garantir que un único ficheiro executable se executa en sistemas Windows e Unix, un truco consiste en codificar ficheiros Windows PE como scripts de shell, aproveitando o feito de que Thompson Shell non usa o marcador de script "#!". Para crear programas que inclúan varios ficheiros (enlazando todos os recursos nun só ficheiro), admite a formación dun ficheiro executable en forma de arquivo ZIP deseñado especialmente. Esquema do formato proposto (exemplo da aplicación hello.com):

MZqFpD='BIOS BOOT SECTOR' exec 7 $(comando -v $0) printf '\177ELF...LINKER-ENCODED-FREEBSD-HEADER' >&7 exec "$0" "$@" exec qemu-x86_64 "$0" "$ @" saír do 1 MODO REAL... SEGMENTOS ELF... NOTA OPENBSD... ENCABEZADORES MACHO... CÓDIGO E DATOS... DIRECTORIO ZIP...

Ao comezo do ficheiro, indícase a etiqueta "MZqFpD", que se percibe como unha cabeceira de formato Windows PE. Esta secuencia tamén está decodificada na instrución “pop %r10; jno 0x4a ; jo 0x4a", e a liña "\177ELF" á instrución "jg 0x47", que se usan para reenviar ao punto de entrada. Os sistemas Unix executan código shell que usa o comando exec, pasando o código executable a través dunha canalización sen nome. Unha limitación do método proposto é a capacidade de executarse en sistemas operativos tipo Unix só usando shells que admitan o modo de compatibilidade Thompson Shell.

A chamada qemu-x86_64 ofrece portabilidade adicional e permite que o código compilado para a arquitectura x86_64 funcione en plataformas que non sexan x86, como placas Raspberry Pi e dispositivos Apple equipados con procesadores ARM. O proxecto tamén se pode usar para crear aplicacións autónomas que se executen sen un sistema operativo (bare metal). Nestas aplicacións, un cargador de arranque está anexo ao ficheiro executable e o programa actúa como un sistema operativo de arranque.

A biblioteca C estándar libc desenvolvida polo proxecto ofrece 2024 funcións (na primeira versión había unhas 1400 funcións). En termos de rendemento, Cosmopolitan funciona tan rápido como a glibc e está notablemente por diante de Musl e Newlib, a pesar de que Cosmopolitan é unha orde de magnitude menor en tamaño de código que a glibc e corresponde aproximadamente a Musl e Newlib. Para optimizar funcións chamadas frecuentemente como memcpy e strlen, utilízase adicionalmente a técnica de "performance de goteo", na que se usa unha ligazón de macro para chamar á función, na que se informa ao compilador sobre os rexistros da CPU implicados na execución do código. proceso, que permite aforrar recursos ao gardar o estado da CPU ao gardar só rexistros modificables.

Entre os cambios na nova versión:

  • Cambiouse o esquema de acceso aos recursos internos dentro dun ficheiro zip (ao abrir ficheiros utilízanse agora os camiños habituais /zip/... en lugar de utilizar o prefixo zip:..). Do mesmo xeito, para acceder aos discos en Windows, é posible utilizar camiños como "/c/..." en lugar de "C:/...".
  • Propúxose un novo cargador APE (Actually Portable Executable), que define o formato dos ficheiros executables universais. O novo cargador usa mmap para colocar o programa na memoria e xa non cambia o contido sobre a marcha. Se é necesario, o ficheiro executable universal pódese converter en ficheiros executables normais vinculados a plataformas individuais.
  • Na plataforma Linux, é posible usar o módulo do núcleo binfmt_misc para executar programas APE. Nótese que usar binfmt_misc é o método de lanzamento máis rápido.
  • Para Linux, propúxose unha implementación da funcionalidade das chamadas de sistema pledge() e unveil() desenvolvidas polo proxecto OpenBSD. Ofrécese unha API para usar estas chamadas en programas en C, C++, Python e Redbean, así como unha utilidade pledge.com para illar procesos arbitrarios.
  • A compilación usa a utilidade Landlock Make, unha edición de GNU Make cunha comprobación de dependencias máis rigorosa e o uso da chamada ao sistema Landlock para illar o programa do resto do sistema e mellorar a eficiencia do caché. Como opción, mantense a posibilidade de construír con GNU Make normal.
  • Implementáronse funcións para multithreading: _spawn() e _join(), que son ligazóns universais sobre API específicas de diferentes sistemas operativos. Tamén se está a traballar para implementar o soporte de fíos POSIX.
  • É posible usar a palabra clave _Thread_local para usar almacenamento separado para cada fío (TLS, Thread-Local Storage). De forma predeterminada, o tempo de execución C inicializa TLS para o fío principal, o que provocou que o tamaño mínimo do executable aumentase de 12 KB a 16 KB.
  • Engadiuse soporte aos parámetros "--ftrace" e "--strace" aos ficheiros executables para obter información sobre todas as chamadas de función e chamadas ao sistema a stderr.
  • Engadido soporte para a chamada do sistema closefrom(), compatible con Linux 5.9+, FreeBSD 8+ e OpenBSD.
  • Na plataforma Linux, o rendemento das chamadas clock_gettime e gettimeofday aumentou ata 10 veces mediante o mecanismo vDSO (obxecto dinámico virtual compartido), que permite mover o controlador de chamadas do sistema ao espazo do usuario e evitar cambios de contexto.
  • As funcións matemáticas para traballar con números complexos foron movidas da biblioteca Musl. O traballo de moitas funcións matemáticas foi acelerado.
  • Propúxose a función nointernet() para desactivar as capacidades da rede.
  • Engadíronse novas funcións para engadir cadeas de forma eficiente: appendd, appendf, appendr, appends, appendw, appendz, kappendf, kvappendf e vappendf.
  • Engadiuse unha versión protexida da familia de funcións kprintf(), deseñada para funcionar con privilexios elevados.
  • Mellorouse significativamente o rendemento das implementacións SSL, SHA, curve25519 e RSA.

Fonte: opennet.ru

Engadir un comentario