Proyecto de Software de Base

El objetivo del proyecto es el de escribir un ensamblador simple para el microprocesador RS08 de Motorola/Freescale. El ensamblador se irá construyendo en diversas etapas. Cada etapa estará especificada en esta página y tendrá una fecha de entrega. La evaluación de la etapa se hará en base a que lo entregado satisfaga exactamente las especificaciones requeridas, es decir, ni más ni menos. Finalmente, cada una de las etapas tendrá un valor que será anunciado junto con la especificación.

Primera etapa: Convertidor de archivo binario a formato de registros S : 10 puntos : 28 de mayo de 2007 a las 22:00.

Deberán escribir un programa llamado binmotZZ.c o binmotZZ.cpp o binmotZZ.java que transforme un archivo binario en un archivo de código objeto en el formato de registros S de Motorola. El código objeto tiene tres tipos de registros: el registro de encabezado (S0 record), el registro de datos (S1 record) y el registro de fin (S5 record). Estos tipos de registros están descritos aquí. Por favor vean los ejemplos en esa página para entender cómo se calcula el campo checksum.

El programa binmotZZ deberá recibir dos parámetros en la lí­nea de instrucciones: fuente y destino (en ese orden), donde fuente es el nombre de un archivo binario existente y destino es el nombre del archivo donde se escribirá el archivo en hexadecimal. Además, podrá recibir un tercer parámetro opcional desplazamiento (que será la dirección de inicio del primer byte del archivo fuente y cuyo valor por omisión será 0x0000) y un cuarto parámetro opcional longitud (cuyo valor por omisión es $20). El desplazamiento y la longitud podrán aparecer escritos en binario, decimal o hexadecimal en los formatos descritos en la tarea 1 excepto que binario se especificará con un signo - en lugar de un % y hexadecimal con un signo + en lugar de un $ (ver el ejemplo abajo).

Si no se dan dos parámetros el programa deberá imprimir en stderr el mensaje "uso: binmot fuente destino [desplazamiento] [longitud]" y terminar. Si el archivo fuente no existe deberá imprimir en stderr el mensaje "error: el archivo fuente no existe" y terminar. Si el archivo destino no se puede crear deberá imprimir en stderr el mensaje "error: el archivo destino no se puede crear" y terminar. Si el desplazamiento no está en el rango $0000 a $FFFF o está en formato equivocado deberá imprimir en stderr el mensaje "error: desplazamiento ilegal" y terminar. Si la longitud no está en el rango $01 a $FC o está en formato equivocado deberá imprimir en stderr el mensaje "error: longitud ilegal" y terminar.

Si no ocurrió ninguno de estos errores, entonces su programa deberá comenzar a leer bytes del archivo fuente  y a escribir registros de datos en el archivo destino. El campo de datos del registro de encabezado deberá contener el nombre del archivo fuente. El campo de datos de cada registro de datos debe ser tan largo como sea posible según el valor de longitud (es decir, sólo el último registro de datos puede tener menos datos que longitud). Al terminar de leer los datos de fuente se deberá escribir un registro de fin de archivo en destino (observe que sólo se contarán los registros de tipo S1 porque no habrá registros de tipos S2 o S3). Si ocurrió algún error al escribir al archivo destino se deberá imprimir en stderr el mensaje "error: no se puede escribir en destino" y terminar. Si todo salió bien, el programa deberá terminar sin emitir ningún mensaje.

Ejemplo: Supongamos que quieren ejecutar el programa binmot con el archivo fuente entrada.txt, el archivo destino salida.txt, el desplazamiento $1000 (en hexadecimal) y la longitud %1010 (en binario) entonces la lí­nea de instrucción deberá ser binmot entrada.txt salida.txt +1000 -1010 después de lo cual el archivo destino deberá contener salida.txt. Nota 1: Para ver cómo se le pueden enviar parámetros a un programa en la lí­nea de instrucciones consulte la sección 5.10 del libro El lenguaje de programación C (Segunda edición) de Kernighan y Ritchie. Aquí­ hay un ejemplo. Nota 2: Si las direcciones llegaran a sobrepasar el valor $FFFF entonces continuarán en la dirección $0000. Nota 3: En el RS08 las direcciones en realidad van de $0000 a $3FFF (es decir, son de 14 bits). Nota 4: Sus programas serán compilados con alguna de las siguientes líneas:
gcc -lm binmotZZ.c -o binmotZZ
g++ -lm -include /usr/include/stdlib.h -Wno-deprecated binmotZZ.cpp -o binmotZZ
gcj --main=binmotZZ -Wall binmotZZ.java -o binmotZZ
fpc binmotZZ.pas -obinmotZZ

Segunda etapa: Ensamblador simple de un paso : 15 puntos : 7 de junio de 2007 a las 22:00.

Deberán escribir un programa llamado unpasoZZ.c o unpasoZZ.cpp o unpasoZZ.java que lea un código fuente en ensamblador y escriba el código objeto correspondiente. En esta etapa del proyecto sólo se considerarán los modos de direccionamiento inherente, inmediato y directo del RS08 (los cuales están abreviados como INH, IMM y DIR en las secciones 2.3 y 2.6 del RS08 Family Reference Manual o en la sección 8.5 del RS08 Microcontrollers Data Sheet).

El programa unpasoZZ recibirá dos parámetros fuente y objeto en la línea de instrucción, donde fuente es el nombre del archivo de texto que contiene el código fuente y objeto es el nombre del archivo de texto donde se escribirá el código objeto. El código fuente consistirá de una sucesión de líneas de texto y terminará con el fin de archivo. Cada línea de texto podrá:
  1. Estar en blanco (los caracteres definidos por isspace).
  2. Contener además de blancos un nemónico.
  3. Contener además de blancos un nemónico separado por blancos de su parámetro numérico.
  4. Contener además de blancos la directiva START separada por blancos de su parámetro numérico.
  5. Contener además de blancos la directiva COM separada por blancos de su parámetro alfanumérico.
  6. Contener además de blancos la directiva END.
Los nemónicos se obtendrán de los mostrados en la sección 2.6 del RS08 Family Reference Manual o en la sección 8.5 del RS08 Microcontrollers Data Sheet de la siguiente manera:
Los nemónicos deberán estar contenidos en una tabla de dispersión como la de la tarea 2. Los parámetros numéricos podrán aparecer escritos en binario, decimal o hexadecimal como en los formatos descritos en la tarea 1. Observe que algunos nemónicos tomarán un parámetro de 8 bits (direccionamientos inmediato y directo) mientras que otros no tomarán parámetros (direccionamiento inherente).

Si la primera instrucción del código fuente no va precedida de una directiva START se debe suponer que tiene la dirección $0000. El parámetro de la directiva COM es un comentario y por lo tanto deberá de ser ignorado. La directiva END indica que el código fuente ha terminado y que las siguientes líneas deben de ser ignoradas.

Su programa deberá detectar los siguientes tipos de errores, los cuales deberá señalar en el error estándar (stderr) junto con el número de la línea fuente donde ocurren:
  1. Instrucción desconocida.
  2. Falta parámetro.
  3. Sobra parámetro.
  4. Parámetro fuera de rango.
  5. Parámetro sin instrucción.
  6. Formato desconocido de parámetro.
Su programa deberá terminar en cuanto se lea la directiva END o se detecte el fin de archivo o el primer error. Las líneas que contienen nemónicos y que no contienen errores generarán código objeto. Cada registro de datos del código objeto será tan largo como sea posible pero nunca deberá tener una longitud mayor a $20 (que era el valor por omisión en la primera etapa del proyecto). Cuando se detecte un error se deberá imprimir en stderr la cadena "ERROR: ", seguida del número de línea donde ocurrió el error y seguida de una de las cadenas " INSTRUCCION", " FALTA", " SOBRA", " RANGO", " PARAMETRO" o " FORMATO" según el tipo de error. Abajo encontrará un ejemplo del funcionamiento de este programa:

Código fuente (ejemplo.asm)
Bytes generados
Código objeto (ejemplo.obj)
COM EJEMPLO

START $0100
NOP
LDAI 10
LDA $8c
COM SEGUNDO
START $0200
SEC
NOP
ADCI %011
ADC $8c
START $1000
CLC
SUBI $5a
SBC %1001
COM AQUI ACABA
END

Esto ya no se lee, pero
lo siguiente marcaria
algun tipo de error:

ZZZ (instruccion desconocida)
LDA (falta parametro)
NOP $00 (sobra parametro)
LDA $100 (parametro fuera de rango)
$100 (parametro sin instruccion)
LDA %12 (formato desconocido de parametro)
-
-
-
AC
A6 0A
B6 8C
-
-
39
AC
A9 03
B9 8C
-
38
A0 5A
B2 09
-
-

S00E0000656A656D706C6F2E61736D95
S1080100ACA60AB68C58
S109020039ACA903B98C1E
S108100038A05AB209FA
S5030003F9

Tercera etapa: Ensamblador de un paso con etiquetas : 15 puntos : 28 de junio de 2007 a las 22:00.

Deberán escribir un programa llamado etiquetaZZ.c o etiquetaZZ.cpp o etiquetaZZ.java que lea un código fuente en ensamblador y escriba el código objeto correspondiente. En esta etapa del proyecto se deberán considerar los modos de direccionamiento pequeño, corto, extendido e indexado del RS08 (los cuales están abreviados como TNY, SRT, EXT e IX en las secciones 2.3 y 2.6 del RS08 Family Reference Manual o en la sección 8.5 del RS08 Microcontrollers Data Sheet) además de los modos ya considerados en la segunda etapa.

El programa etiquetaZZ recibirá dos parámetros fuente y objeto en la línea de instrucción, donde fuente es el nombre del archivo de texto que contiene el código fuente y objeto es el nombre del archivo de texto donde se escribirá el código objeto. El código fuente consistirá de una sucesión de líneas de texto y terminará con el fin de archivo. Cada línea de texto podrá:
  1. Estar en blanco (los caracteres definidos por isspace).
  2. Contener además de blancos un nemónico.
  3. Contener además de blancos un nemónico separado por blancos de su parámetro numérico.
  4. Contener además de blancos la directiva DATA seguida de sus parámetros numéricos separados por blancos.
  5. En los cuatro casos anteriores podrá contener una etiqueta antes de cualquier otro campo separada por blancos.
  6. Contener además de blancos la directiva START separada por blancos de su parámetro numérico.
  7. Contener además de blancos la directiva COM separada por blancos de su parámetro alfanumérico.
  8. Contener además de blancos una etiqueta separada por blancos de la directiva EQU separada por blancos de un parámetro numérico.
  9. Contener además de blancos la directiva END.
Puede suponer que todas las etiquetas miden un máximo de 8 caracteres.

Los nemónicos se obtendrán de los mostrados en la sección 2.6 del RS08 Family Reference Manual o en la sección 8.5 del RS08 Microcontrollers Data Sheet de la siguiente manera: Los nemónicos deberán estar contenidos en una tabla de dispersión como la de la tarea 2. Los parámetros numéricos podrán ser etiquetas definidas previamente (ya sea en una línea que contiene un nemónico o alguna de las directivas DATA o EQU) o aparecer escritos en binario, decimal o hexadecimal como en los formatos descritos en la tarea 1. Note que los nemónicos y las directivas van en mayúsculas pero las etiquetas van en minúsculas.

Observe que algunos nemónicos tomarán un parámetro de 4 bits (direccionamiento pequeño), de 5 bits (direccionamiento corto), de 8 bits (direccionamientos inmediato y directo) o de 14 bits (direccionamiento extendido) mientras que otros no tomarán parámetros (direccionamientos inherente e indexado). En los primeros dos casos los bits del parámetro modifican los 4 o 5 bits más bajos del código de operación, en el tercer caso los bits del parámetro son un segundo byte de la instrucción y en el cuarto caso los bits del parámetro están en el segundo y tercer byte de la instrucción (los 6 bits más altos del operando en el segundo y los 8 bits más bajos en el tercero).

El primer parámetro numérico (de 8 bits) de la directiva DATA es el número de bytes que se colocarán en el código objeto y su valor indica cuántos parámetros numéricos adicionales (de 8 bits) tiene la directiva y que deberán colocarse en el código objeto en ese orden. El parámetro numérico de la directiva EQU es el valor que se le asignará a la etiqueta a su izquierda.

Además de los errores detectados en la segunda etapa del proyecto, se deberán detectar los siguientes tipos de errores:
  1. Si una etiqueta aparece dos veces en el lado izquierdo de una línea se está redefiniendo un símbolo.
  2. Si una etiqueta que no ha sido definida previamente aparece como parámetro numérico entonces es un símbolo no definido.
Su programa deberá terminar en cuanto se lea la directiva END o se detecte el fin de archivo o el primer error. Las líneas que contienen nemónicos o la directiva DATA y que no contienen errores generarán código objeto. Cada registro de datos del código objeto será tan largo como sea posible pero nunca deberá tener una longitud mayor a 0x20 (que era el valor por omisión en la primera etapa del proyecto). Cuando se detecte un error se deberá imprimir en stderr la cadena "ERROR: ", seguida del número de línea donde ocurrió el error y seguida de una de las cadenas " INSTRUCCION", " FALTA", " SOBRA", " RANGO", " PARAMETRO", " FORMATO", " CONOCIDO" o " DESCONOCIDO" según el tipo de error. Abajo encontrará un ejemplo del funcionamiento de este programa:

Código fuente (ejem2.asm)
Bytes generados
Código objeto (ejem2.obj)
hola EQU $1234
peque EQU %1001
corto EQU 20
exten EQU hola
START hola
LDAS corto
atras LDAX
ADDT peque
JMP exten
DATA 3 peque corto $99
JMP atras
END

Esto ya no se lee, pero
lo siguiente marcaria
algun tipo de error:

DATA 3 peque corto (falta parametro)
DATA 2 peque corto $99 (sobra parametro)
ADDT corto (parametro fuera de rango)
LDAS $3F (parametro fuera de rango)
JMP $4000 (parametro fuera de rango)
exten EQU $1234 (simbolo redefinido)
JMP adios (simbolo no definido)
-
-
-
-
-
D4
CE
69
BC 12 34
09 14 99
BC 12 35
-
S00C0000656A656D322E61736DB1
S10F1234D4CE69BC1234091499BC1235E4
S5030001FB

Cuarta etapa: Ensamblador de dos pasos : 10 puntos : 16 de julio de 2007 a las 22:00.

Deberán escribir un programa llamado dospasosZZ.c o dospasosZZ.cpp o dospasosZZ.java que lea un código fuente en ensamblador y escriba el código objeto correspondiente. En esta etapa del proyecto se deberán considerar el modo de direccionamiento relativo del RS08 (el cual está abreviado como REL en las secciones 2.3 y 2.6 del RS08 Family Reference Manual o en la sección 8.5 del RS08 Microcontrollers Data Sheet) además de los modos ya considerados en la tercera etapa.

El programa dospasosZZ recibirá dos parámetros fuente y objeto en la línea de instrucción, donde fuente es el nombre del archivo de texto que contiene el código fuente y objeto es el nombre del archivo de texto donde se escribirá el código objeto. El código fuente consistirá de una sucesión de líneas de texto y terminará con el fin de archivo. Cada línea de texto podrá ser como en los 9 casos de la tercera etapa del proyecto o bien:
  1. contener además de blancos la directiva RES separada por blancos de un parámetro numérico. La directiva RES puede estar separada por blancos de una etiqueta.
Los nemónicos de las instrucciones relativas se tomarán sin cambios de los mostrados en las secciones 2.3 y 2.6 del RS08 Family Reference Manual o en la sección 8.5 del RS08 Microcontrollers Data Sheet. Los nemónicos deberán estar contenidos en una tabla de dispersión como la de la tarea 2. Los parámetros numéricos podrán ser etiquetas (referencias hacia adelante o hacia atrás o definidas con alguna de las directivas DATA o EQU) o aparecer escritos en binario, decimal o hexadecimal como en los formatos descritos en la tarea 1.

Las instrucciones de direccionamiento relativo tomarán un parámetro de 14 bits pero sólo generarán en el código objeto una dirección relativa de 8 bits con signo (en complemento a 2) calculada de la siguiente forma: se calcula la resta (parámetro de 14 bits) menos (contador de localidades actual + 2) y ese valor debe de estar en el rango -128 a 127.

El parámetro numérico de la directiva RES es un número de 14 bits que se le sumará al valor actual del contador de localidades, por lo que el efecto de esta directiva es el de reservar la cantidad especificada de bytes. Observe que esta directiva no genera código objeto: el registro de texto actual debe terminar de procesarse y comenzarse uno nuevo a partir de la nueva dirección recién calculada.

Respecto a las etiquetas, el último tipo de error cambia a
  1. si una etiqueta que no ha sido definida en ninguna parte del código fuente aparece como parámetro numérico entonces es un símbolo no definido.
Su programa deberá terminar en cuanto se lea la directiva END o se detecte el fin de archivo o el primer error. Las líneas que contienen nemónicos o la directiva DATA y que no contienen errores generarán código objeto. Cada registro de datos del código objeto será tan largo como sea posible pero nunca deberá tener una longitud mayor a 0x20 (que era el valor por omisión en la primera etapa del proyecto). Cuando se detecte un error se deberá imprimir en stderr la cadena "ERROR: ", seguida del número de línea donde ocurrió el error y seguida de una de las cadenas " INSTRUCCION", " FALTA", " SOBRA", " RANGO", " PARAMETRO", " FORMATO", " CONOCIDO" o " DESCONOCIDO" según el tipo de error.