Asignar o ajustar direcciones en tiempo de ejecución
La reubicación es el proceso de asignar direcciones de carga para códigos y datos dependientes de la posición de un programa y ajustar el código y los datos para reflejar las direcciones asignadas. [1] [2] Antes de la llegada de los sistemas multiproceso, y todavía en muchos sistemas integrados, las direcciones de los objetos eran absolutas y comenzaban en una ubicación conocida, a menudo cero. Dado que los sistemas multiprocesamiento se vinculan y cambian dinámicamente entre programas, se hizo necesario poder reubicar objetos utilizando código independiente de la posición . Un vinculador generalmente realiza la reubicación junto con la resolución de símbolos , el proceso de buscar archivos y bibliotecas para reemplazar referencias simbólicas o nombres de bibliotecas con direcciones reales utilizables en la memoria antes de ejecutar un programa.
La reubicación normalmente la realiza el vinculador en el momento del enlace , pero también puede realizarse en el momento de la carga mediante un cargador de reubicación , o en tiempo de ejecución mediante el propio programa en ejecución . Algunas arquitecturas evitan por completo la reubicación al diferir la asignación de direcciones al tiempo de ejecución; como, por ejemplo, en máquinas de pila con aritmética de dirección cero o en algunas arquitecturas segmentadas donde cada unidad de compilación se carga en un segmento separado.
La tabla de reubicación es una lista de punteros creados por el traductor (un compilador o ensamblador ) y almacenados en el objeto o archivo ejecutable. Cada entrada en la tabla, o "reparación", es un puntero a una dirección absoluta en el código objeto que debe cambiarse cuando el cargador reubica el programa para que haga referencia a la ubicación correcta. Las reparaciones están diseñadas para respaldar la reubicación del programa como una unidad completa. En algunos casos, cada corrección en la tabla es en sí misma relativa a una dirección base de cero, por lo que las correcciones en sí deben cambiarse a medida que el cargador se mueve a través de la tabla. [2]
En algunas arquitecturas, una corrección que cruza ciertos límites (como el límite de un segmento) o que no está alineada en el límite de una palabra es ilegal y el vinculador la marca como un error. [3]
En cambio, los segmentos son valores relativos en el archivo EXE de DOS. Estos segmentos deben corregirse cuando el ejecutable se haya cargado en la memoria. El cargador EXE utiliza una tabla de reubicación para encontrar los segmentos que deben ajustarse.
Ventanas de 32 bits
Con los sistemas operativos Windows de 32 bits, no es obligatorio proporcionar tablas de reubicación para los archivos EXE, ya que son la primera imagen cargada en el espacio de direcciones virtuales y, por lo tanto, se cargarán en su dirección base preferida.
Tanto para las DLL como para los EXE que optan por la aleatorización del diseño del espacio de direcciones (ASLR), una técnica de mitigación de exploits introducida con Windows Vista , las tablas de reubicación una vez más se vuelven obligatorias debido a la posibilidad de que el binario se pueda mover dinámicamente antes de ejecutarse, a pesar de que siguen siendo lo primero que se carga en el espacio de direcciones virtuales.
Ventanas de 64 bits
Cuando se ejecutan archivos binarios nativos de 64 bits en Windows Vista y superiores, ASLR es obligatorio [ cita necesaria ] y, por lo tanto, el compilador no puede omitir las secciones de reubicación.
Sistemas tipo Unix
El formato ejecutable Executable and Linkable Format (ELF) y el formato de biblioteca compartida utilizado por la mayoría de los sistemas tipo Unix permiten definir varios tipos de reubicación. [4]
Procedimiento de reubicación
El vinculador lee información de segmentos y tablas de reubicación en los archivos de objetos y realiza la reubicación mediante:
fusionar todos los segmentos de tipo común en un solo segmento de ese tipo
asignar direcciones de tiempo de ejecución únicas a cada sección y cada símbolo, dando a todos los códigos (funciones) y datos (variables globales) direcciones de tiempo de ejecución únicas [ aclaración necesaria ]
refiriéndose a la tabla de reubicación para modificar [ ¿por qué? ] símbolos para que apunten a las direcciones de tiempo de ejecución correctas [ se necesita aclaración ] .
Ejemplo
El siguiente ejemplo utiliza la arquitectura MIX de Donald Knuth y el lenguaje ensamblador MIXAL. Los principios son los mismos para cualquier arquitectura, aunque los detalles cambiarán.
(A) El programa SUBR se compila para producir el archivo objeto (B), que se muestra como código de máquina y ensamblador. El compilador puede iniciar el código compilado en una ubicación arbitraria, a menudo en la ubicación 1, como se muestra. La ubicación 13 contiene el código de máquina para la instrucción de salto a la declaración ST en la ubicación 5.
(C) Si SUBR se vincula posteriormente con otro código, se puede almacenar en una ubicación distinta de 1. En este ejemplo, el vinculador lo coloca en la ubicación 120. La dirección en la instrucción de salto, que ahora está en la ubicación 133, debe reubicarse para señalar la nueva ubicación del código para la declaración ST , ahora 125. [1 61 que se muestra en la instrucción es la representación del código de máquina MIX de 125].
(D) Cuando el programa se carga en la memoria para ejecutarse, puede cargarse en alguna ubicación distinta a la asignada por el vinculador. Este ejemplo muestra SUBR ahora en la ubicación 300. La dirección en la instrucción de salto, ahora en 313, debe reubicarse nuevamente para que apunte a la ubicación actualizada de ST , 305. [4 49 es la representación de la máquina MIX de 305].
^ "Tipos de código objeto". Manual de referencia del cargador de aplicaciones iRMX 86 (PDF) . Intel . págs. 1-2–1-3. Archivado (PDF) desde el original el 11 de enero de 2020 . Consultado el 11 de enero de 2020 . […] El código absoluto , y un módulo de objeto absoluto, es código que ha sido procesado por LOC86 para ejecutarse solo en una ubicación específica de la memoria. El cargador carga un módulo de objeto absoluto solo en la ubicación específica que debe ocupar el módulo. El código independiente de la posición (comúnmente conocido como PIC) se diferencia del código absoluto en que el PIC se puede cargar en cualquier ubicación de la memoria. La ventaja de PIC sobre el código absoluto es que PIC no requiere que usted reserve un bloque de memoria específico. Cuando el cargador carga PIC, obtiene segmentos de memoria iRMX 86 del grupo del trabajo de la tarea que realiza la llamada y carga el PIC en los segmentos. Una restricción relativa al PIC es que, como en el modelo de segmentación COMPACT PL/M-86 […], sólo puede tener un segmento de código y un segmento de datos, en lugar de dejar que las direcciones base de estos segmentos y, por tanto, los segmentos mismos , varían dinámicamente. Esto significa que los programas PIC tienen necesariamente menos de 64 Kbytes de longitud. El código PIC se puede producir mediante el control BIND de LINK86. El código localizable en tiempo de carga (comúnmente conocido como código LTL) es la tercera forma de código objeto. El código LTL es similar al PIC en que el código LTL se puede cargar en cualquier lugar de la memoria. Sin embargo, al cargar código LTL, el cargador cambia la parte base de los punteros para que sean independientes del contenido inicial de los registros en el microprocesador. Debido a esta corrección (ajuste de direcciones base), el código LTL puede usarse en tareas que tengan más de un segmento de código o más de un segmento de datos. Esto significa que los programas LTL pueden tener más de 64 KB de longitud. FORTRAN 86 y Pascal 86 producen automáticamente código LTL, incluso para programas cortos. El código LTL se puede producir mediante el control BIND de LINK86. […]
^ ab Levine, John R. (2000) [octubre de 1999]. "Capítulo 1: Vinculación y carga y Capítulo 3: Archivos objeto". Enlazadores y cargadores. La serie Morgan Kaufmann sobre programación e ingeniería de software (1 ed.). San Francisco, California, Estados Unidos: Morgan Kaufmann . pag. 5.ISBN1-55860-496-0. OCLC 42413382. Archivado desde el original el 5 de diciembre de 2012 . Consultado el 12 de enero de 2020 .Código: [1][2] Fe de erratas: [3]
^ Borland (1 de septiembre de 1999) [2 de julio de 1998]. "Artículo de Borland n.º 15961: Cómo afrontar los mensajes de 'Reparación de desbordamiento'". comunidad.borland.com . Base de datos de información técnica - Producto: Borland C++ 3.1. TI961C.txt #15961. Archivado desde el original el 7 de julio de 2008 . Consultado el 15 de enero de 2007 .
^ "Formato ejecutable y vinculable (ELF)" (PDF) . skyfree.org . Especificación de formatos portátiles de estándares de interfaz de herramientas (TIS), versión 1.1. Archivado (PDF) desde el original el 24 de diciembre de 2019 . Consultado el 1 de octubre de 2018 .
Otras lecturas
Johnson, Glenn (21 de diciembre de 1975) [13 de noviembre de 1975]. 11/34 Prueba de lógica básica de gestión de memoria. Corporación de Equipos Digitales (DEC). MAINDEC-11-DFKTA-AD . Consultado el 19 de agosto de 2017 .
Formaniak, Peter G.; Leitch, David (julio de 1977). "Un estándar de software de microprocesador propuesto". BYTE : la pequeña revista de sistemas . Foro Técnico. vol. 2, núm. 7. Peterborough, New Hampshire, EE.UU.: Byte Publications, Inc. págs. 34, 62–63. arca:/13960/t32245485 . Consultado el 6 de diciembre de 2021 .(3 páginas) (NB. Describe un formato hexadecimal reubicable de Mostek ).
Ogdin, Carol Anne; Colvin, Neil; Pittman, Tom; Tubb, Philip (noviembre de 1977). "Formatos de código de objetos reubicables". BYTE : la pequeña revista de sistemas . Foro Técnico. vol. 2, núm. 11. Peterborough, New Hampshire, EE.UU.: Byte Publications, Inc. págs. 198-205. arca:/13960/t59c88b4h, arca:/13960/t3kw76j24 . Consultado el 6 de diciembre de 2021 .(8 páginas) (NB. Describe un formato hexadecimal reubicable por TDL ).
Kildall, Gary Arlen (febrero de 1978) [1976]. "Una técnica sencilla para la reubicación estática de código de máquina absoluto". Revista del Dr. Dobb sobre calistenia y ortodoncia informática . 3 (2). Compañía de Computación del Pueblo : 10–13 (66–69). ISBN 0-8104-5490-4. #22 arca:/13960/t8hf1g21p . Consultado el 19 de agosto de 2017 .[4][5][6]. Presentado originalmente en: Kildall, Gary Arlen (1977) [22-24 de noviembre de 1976]. "Una técnica simple para la reubicación estática de código de máquina absoluto". Escrito en la Escuela Naval de Postgrado , Monterey, California, EE.UU. En Tito, Harold A. (ed.). Registro de la conferencia: Décima Conferencia Anual de Asilomar sobre circuitos, sistemas y computadoras: artículos presentados del 22 al 24 de noviembre de 1976. Conferencia de Asilomar sobre señales, sistemas y computadoras . Asilomar Hotel and Conference Grounds, Pacific Grove, California, EE.UU.: Western Periodicals Company. págs. 420–424. ISSN 1058-6393 . Consultado el 6 de diciembre de 2021 .(609 páginas). (Este método de "cambio de tamaño", llamado reubicación de límites de página , podría aplicarse estáticamente a una imagen de disco CP/M-80 usando MOVCPM [pl] para maximizar el TPA para que se ejecuten los programas. También fue utilizado dinámicamente por el CP/ M debugger Herramienta de depuración dinámica (DDT) para reubicarse en una memoria superior. El mismo enfoque fue desarrollado de forma independiente por Bruce H. Van Natta de IMS Associates para producir código PL/M reubicable. Como reubicación de límites de párrafo , se desarrolló más tarde otra variante de este método. Utilizado por TSR de reubicación automática de HMA dinámicamente como KEYB , SHARE y NLSFUNC en DR DOS 6.0 y superiores. Matthias R. Paul y Axel concibieron e implementaron de forma independiente un método granular de nivel de bytes mucho más sofisticado basado en un enfoque algo similar. C. Frinke por su eliminación dinámica de códigos muertos para minimizar dinámicamente la huella de tiempo de ejecución de los controladores residentes y TSR (como FreeKEYB).
Mossip, Richard H. (septiembre-octubre de 1980). Escrito en Bloomingdale, Nueva Jersey, Estados Unidos. "Código reubicable" (PDF) . Microsistemas S-100 . vol. 1, núm. 5. Mountainside & Springfield, Nueva Jersey, EE. UU.: Libes, Inc. págs. 54–55. ISSN 0199-7955. arca:/13960/s2cfgkmxcwg. arca:/13960/s2qdm1t01nr. Archivado (PDF) desde el original el 27 de noviembre de 2023 . Consultado el 27 de noviembre de 2023 .[7][8] (2 páginas) (NB. Describe la reubicación de límites de página y la reubicación de ensambladores).
Huitt, Robert; Eubanks, Gordon ; Rolander, Thomas "Tom" Alan ; Leyes, David; Michel, Howard E.; Halla, Brian; Wharton, John Harrison ; Berg, Brian; Su, Weilian; Kildall, Scott ; Kampe, Bill (25 de abril de 2014). Leyes, David (ed.). "El legado de Gary Kildall: la dedicación al hito de CP/M IEEE" (PDF) (transcripción del vídeo). Pacific Grove, California, Estados Unidos: Museo de Historia de la Computación . Número de referencia CHM: X7170.2014. Archivado (PDF) desde el original el 27 de diciembre de 2014 . Consultado el 19 de enero de 2020 . […] Leyes: […] "reubicación dinámica" del sistema operativo. ¿Puedes decirnos qué es eso y por qué era importante? […] Eubanks : […] lo que hizo Gary […] fue […] alucinante. […] Recuerdo el día en la escuela que entró saltando al laboratorio y dijo: Ya he descubierto cómo mudarme. Aprovechó el hecho de que el único byte siempre sería el byte de orden superior . Y entonces creó un mapa de bits . […] no importaba cuánta memoria tuviera la computadora, el sistema operativo siempre se podía mover a la memoria alta. Por lo tanto, se podría comercializar esto […] en máquinas de diferentes cantidades de memoria. […] no se podría estar vendiendo un CP/M de 64K y un CP/M de 47K. Sería simplemente ridículo tener una compilación completa en las direcciones. Así que Gary se dio cuenta de esto una noche, probablemente en medio de la noche, pensando en algo de codificación, y esto realmente hizo posible la comercialización de CP/M. Realmente creo que sin esa reubicación hubiera sido un problema muy difícil. Conseguir que la gente lo compre, les parecería complicado, y si añadieras más memoria tendrías que buscar un sistema operativo diferente. […] Intel […] tenía los bytes invertidos , verdad, para las direcciones de memoria. Pero siempre estaban en el mismo lugar, por lo que podías reubicarlos en un límite de 256 bytes , para ser precisos. Por lo tanto, siempre puedes reubicarlo con solo un mapa de bits de dónde están esas […] Leyes: Sin duda, la explicación más elocuente que he tenido sobre la reubicación dinámica […][9][10] (33 páginas)
Liber, Eckhard; Von Massenbach, Thomas (1987). "CP/M 2 lernt dazu. Modulare Systemerweiterungen auch für das 'alte' CP/M". c't - magazin für computertechnik (parte 1) (en alemán). 1987 (1). Heise Verlag : 124-135; Liber, Eckhard; Von Massenbach, Thomas (1987). "CP/M 2 lernt dazu. Modulare Systemerweiterungen auch für das 'alte' CP/M". c't - magazin für computertechnik (parte 2) (en alemán). 1987 (2). Heise Verlag : 78–85; Huck, Alex (9 de octubre de 2016). "RSM para CP/M 2.2". DDR de computadora doméstica (en alemán). Archivado desde el original el 25 de noviembre de 2016 . Consultado el 25 de noviembre de 2016 .
Guzis, Charles "Chuck" P. (16 de marzo de 2015). "Re: programación en lenguaje ensamblador CP/M". Foro de informática antigua . Género: CP/M y MP/M. Archivado desde el original el 1 de febrero de 2020 . Consultado el 1 de febrero de 2020 . […] ¿Alguna vez te has preguntado cómo funciona MOVCPM [pl] ? Dado que BDOS y CCP tienen mucha memoria, por encima de la aplicación de usuario, las direcciones deben cambiarse cada vez que se cambia el tamaño de la memoria del sistema. Eso requiere reubicar direcciones en código 8080 , ya que el direccionamiento relativo no es parte del hardware. Sin implementar un ensamblador y cargador de reubicación completo, ¿cómo se hace esto? En realidad, es bastante inteligente y MP/M incluso utiliza este esquema para construir sus archivos reubicables por páginas. Simplemente ensambla el programa fuente dos veces con el segundo origen ensamblador 100H (256 bytes) más alto que el primero. Luego se comparan las dos imágenes binarias, byte por byte, y se construye un mapa donde los pares de bytes difieren en valor en exactamente 100H. El resultado es una lista de ubicaciones donde es necesario ajustar el valor de reubicación si se va a mover la ubicación de un programa en la memoria. MP/M llama a este tipo de archivo PRL (página reubicable), pero no sé si CP/M 2.2 alguna vez acuñó un nombre para él. […]
Guzis, Charles "Chuck" P. (29 de julio de 2015). "Re: ¿Cómo funciona MOVCPM.COM?". Foro de informática antigua . Género: CP/M y MP/M. Archivado desde el original el 1 de febrero de 2020 . Consultado el 1 de febrero de 2020 . […] MOVCPM [pl] utiliza un tipo antiguo de formato PRL. Básicamente, CP/M se ensambla dos veces; la segunda vez se compensan 100H bytes. Se comparan los dos binarios y se construye un mapa de bits . Un bit establecido implica que se debe ajustar el byte de orden superior de una dirección. Los bytes de dirección de orden inferior no se ven afectados; por lo tanto, "archivo reubicable de página". Cada byte del mapa de bits corresponde a 8 bytes de los datos binarios. […] Entonces, todo lo que se va a mover en MOVCPM es parte de la imagen y su mapa de bits de reubicación. […]
Guzis, Charles "Chuck" P. (8 de noviembre de 2016). "Re: ¿Es seguro utilizar RST 28h en programas de ensamblaje CP/M?". Foro de informática antigua . Género: CP/M y MP/M. Archivado desde el original el 1 de febrero de 2020 . Consultado el 1 de febrero de 2020 . […] He hecho referencia a archivos PRL y cómo comenzaron originalmente con MOVCPM [pl] , pero se convirtieron en una parte integral de MP/M y CP/M 3.0 . Pero los archivos PRL utilizan un mapa de bits en el que cada bit corresponde a una ubicación de memoria; Un bit indica que se debe agregar un desplazamiento de reubicación de página a la ubicación de memoria correspondiente. Si tiene muy pocas referencias de memoria absoluta (a diferencia de las relativas), es posible que desee emplear una lista de punteros (2 bytes por referencia) en lugar de un mapa de bits. Esto es poco probable en el código 8080 que no tiene saltos relativos, pero puede ser una consideración para el código Z80 . El truco para descubrir esto rápidamente es ensamblar su programa dos veces; la segunda vez compensada en 100H, luego compare los dos binarios. La ventaja de la reubicación en tiempo de ejecución es que no tiene que incurrir en una penalización por el código que intenta solucionar el problema de la reubicación; no hay "trucos"; simplemente escribe código directo. […]
Calingaert, Peter (1979) [5 de noviembre de 1978]. "8.2.2 Reubicación del cargador". Escrito en la Universidad de Carolina del Norte en Chapel Hill . En Horowitz, Ellis (ed.). Ensambladores, compiladores y traducción de programas . Serie de ingeniería de software (primera impresión, 1ª ed.). Potomac, Maryland, EE.UU.: Computer Science Press, Inc. págs. 237–241. ISBN 0-914894-23-4. ISSN 0888-2088. LCCN 78-21905 . Consultado el 20 de marzo de 2020 .(2+xiv+270+6 páginas)
El formato de archivo OBJ de Microsoft. Microsoft , servicios de soporte de productos. Nota de aplicación SS0288. Archivado desde el original el 9 de septiembre de 2017 . Consultado el 21 de agosto de 2017 .
Elliott, John C. (5 de junio de 2012) [2 de enero de 2000]. "Formato de archivo PRL". seasip.info . Archivado desde el original el 26 de enero de 2020 . Consultado el 26 de enero de 2020 . […] Un archivo PRL es un archivo binario reubicable, utilizado por MP/M y CP/M Plus para varios módulos distintos de los archivos .COM . El formato de archivo también se utiliza para archivos FID en Amstrad PCW . Hay varios formatos de archivo que utilizan versiones de PRL: SPR (System PRL), RSP (Proceso del sistema residente). LINK-80 también puede producir archivos OVL ( superposición ), que tienen un encabezado PRL pero no son reubicables. Los controladores GSX están en formato PRL; también lo son las extensiones del sistema residente (.RSX). […][11]
Elliott, John C. (5 de junio de 2012) [2 de enero de 2000]. "Formato REL de Microsoft". seasip.info . Archivado desde el original el 26 de enero de 2020 . Consultado el 26 de enero de 2020 . […] El formato REL es generado por M80 de Microsoft y RMAC de Digital Research . […]
feilipu (05/09/2018) [02/09/2018]. "Soporte para PRL, ejecutable reubicable de página para MP/M". z88dk . Archivado desde el original el 1 de febrero de 2020 . Consultado el 26 de enero de 2020 . […] A partir de los archivos .REL de Microsoft ensamblados , el vinculador debe generar un ejecutable en formato .PRL para MP/M . El formato .PRL es esencialmente un archivo .COM con información adicional para permitir que el programa y sus datos se reubiquen en cualquier página. ¿Cómo se ve un archivo .PRL? Los primeros bytes son el tamaño del programa, seguidos por el origen del programa en 0x0100. Después del programa, se adjunta una máscara bit por byte para permitir que el sistema MP/M sepa qué bytes del programa deben cambiarse cuando se reubica el programa. ¿Cómo hace eso el vinculador sin desmontar toda la aplicación? De antemano el programa está vinculado para dos orígenes diferentes 0x0100 y 0x0200, de los objetos .REL. El truco del enlazador consiste simplemente en reconocer qué bytes difieren en las dos versiones del ejecutable. Luego, estos bytes se registran en la máscara de bits almacenada después del ejecutable, y el programa .PRL final está diseñado para ejecutarse desde 0x0100 más su desplazamiento de página. Se hace el mismo truco para los archivos ejecutables .RSP y .SPR, excepto que ambos formatos renuncian al desplazamiento y se ejecutan desde 0x0000 más su desplazamiento de página. […]
Hermanos, Hardin (abril de 1983). "Comprensión del código reubicable". 80 micrones . El siguiente paso (39). 1001001, Inc .: 38, 40, 42, 45. ISSN 0744-7868 . Consultado el 6 de febrero de 2020 .[12][13]
Hermanos, Hardin (abril de 1985). "Programas reubicables: vagabundos de la microcomputación". 80 micrones . El siguiente paso (63). Comunicaciones CW/Peterborough, Inc .: 98, 100, 102–103. ISSN 0744-7868 . Consultado el 6 de febrero de 2020 .[14][15]
Sage, Jay (mayo-junio de 1988). Carlson, Arte (ed.). "ZCPR 3.4 - Programas tipo 4". The Computer Journal (TCJ): programación, soporte al usuario, aplicaciones . Esquina ZCPR3 (32). Columbia Falls, Montana, EE. UU.: 10–17 [15–16]. ISSN 0748-9331. arca:/13960/t1wd4v943 . Consultado el 29 de noviembre de 2021 .[16][17]
Mitchell, Bridger (julio-agosto de 1988). Carlson, Arte (ed.). "Z3PLUS y reubicación: información sobre ZCPR3PLUS y cómo escribir código Z80 de reubicación automática". The Computer Journal (TCJ): programación, soporte al usuario, aplicaciones . CP/M avanzado (33). Cataratas de Columbia, Montana, EE. UU.: 9–15. ISSN 0748-9331. arca:/13960/t36121780 . Consultado el 9 de febrero de 2020 .[18][19]
Sage, Jay (septiembre-octubre de 1988). Carlson, Arte (ed.). "Más sobre código reubicable, archivos PRL, ZCPR34 y programas Type-4". The Computer Journal (TCJ): programación, soporte al usuario, aplicaciones . Esquina ZCPR3 (34). Cataratas de Columbia, Montana, EE. UU.: 20–25. ISSN 0748-9331. arca:/13960/t0ks7pc39 . Consultado el 9 de febrero de 2020 .[20][21][22]
Sage, Jay (enero-febrero de 1992). Carlson, Arte; McEwen, Chris (eds.). "Diez años de ZCPR". The Computer Journal (TCJ): programación, soporte al usuario, aplicaciones . Esquina del sistema Z (54). S. Plainfield, Nueva Jersey, Estados Unidos: Socrates Press: 3–7. ISSN 0748-9331. arca:/13960/t89g6n689 . Consultado el 29 de noviembre de 2021 .[23][24][25]
Sage, Jay (mayo-junio de 1992) [marzo-junio de 1992]. Carlson, Arte; McEwen, Chris (eds.). "Programas tipo 3 y tipo 4". The Computer Journal (TCJ): programación, soporte al usuario, aplicaciones . Rincón del sistema Z: algunas aplicaciones nuevas de programas tipo 4 (55). S. Plainfield, Nueva Jersey, Estados Unidos: Socrates Press: 13–19. ISSN 0748-9331. arca:/13960/t4dn54d22 . Consultado el 29 de noviembre de 2021 .[26][27]
Ganssle, Jack (febrero de 1992). "Escribir código reubicable: parte del código incrustado debe ejecutarse en más de una dirección". Programación de sistemas integrados . The Ganssle Group: perfeccionando el arte de construir sistemas integrados / TGG. Archivado desde el original el 18 de julio de 2019 . Consultado el 20 de febrero de 2020 .