Procesadores de Macros MIS. Lizbeth Alejandra Hernández González Programación de Sistemas Procesadores de Macros • Una macroinstrucción no es más que una conveniencia notacional para el programador (versión abreviada). • Cada vez que se llama una macro en un programa, el ensamblador, en lugar de la llamada a la macro, copia y pega el código real de la misma (MACROEXPANSIÓN). • Las funciones de un procesador de macros implican la sustitución de un grupo de caracteres o líneas por otras. • El diseño de un procesador de macros no está directamente relacionado con la estructura del computador en el que se va a ejecutar. • El uso más común de los procesadores de macros es en la programación en lenguaje ensamblador, • también se pueden utilizar procesadores de macros con lenguajes de programación de alto nivel, • hay procesadores de macros de aplicación general que no están ligados a ningún lenguaje en particular. Funciones básicas del procesador de macros • Definición, • invocación y • expansión de macros • Ejemplo: programa en ensamblador con macros. • Este programa define y usa dos instrucciones a macros: RDBUFF y WRBUFF. 5 10 15 20 25 30 35 40 45 50 55 60 65 70 75 80 85 90 95 100 105 110 115 120 125 130 135 140 145 150 155 160 165 170 175 180 190 195 200 205 210 215 220 225 230 235 240 245 250 255 COPY START 0 COPIA EL ARCHIVO DE LA ENTRADA A LA SALIDA ROBUFF MACRO &INDEV,&BUFADR,&RECLTH . . MACRO QUE LEE UN REGISTRO EN EL BUFFER . CLEAR X LIMPIA EL CONTADOR DE CICLO CLEAR A CLEAR S +LDT #4096 ASIGNA LA LONGITUD MAXIMA DEL REGISTRO TD =X’&INDEV’ PRUEBA EL DISPOSITIVO DE ENTRADA JEQ *-3 REPITE EL CICLO HASTA QUE ESTE LISTO RD =X’&INDEV’ LEE EL CARÁCTER EN EL REGISTRO A COMPR A,S EXAMINA SI HAY FIN DE REGISTRO JEQ *+11 SALE DEL CICLO SI ES FIN DE REGISTRO STCH $BUFADR,X ALMACENA EL CARÁCTER EN EL BUFFER TIXT T REPITE EL CICLO A MENOS QUE SE HAYA JLT *-19 ALCANZADO LA LONGITUD DEL REGISTRO STX &RECLTH GUARDA LA LONGITUD DEL REGISTRO MEND WRBUFF MACRO &OUTDEV,&BUFADR,&RECLTH . . MACRO QUE ESCRIBE EL REGISTRO DEL BUFFER . CLEAR X LIMPIA EL CONTADOR DE CICLO LDT &RECLTH LDCH &BUFADR,X TOMA EL CARACTER DEL BUFFER TD =X’&OUTDEV’ PRUEBA DEL DISPOSITIVO DE SALIDA JEQ *-3 REPITE EL CICLO HASTA QUE ESTE LISTO WD =X’&OUTDEV’ ESCRIBE EL CARACTER TIXR T REPITE EL CICLO HASTA QUE SE HAYAN JLT *-14 ESCRITO TODOS LOS CARACTERES MEND . . PROGRAMA PRINCIPAL . FIRST STL RETADR GUARDA LA DIRECCIÓN DE RETORNO CLOPP RDBUFF F1,BUFFER,LENGTH LEE EL REGISTRO DE ENTRADA EN EL BUFFER LDA LENGTH VERIFICA SI ES FIN DE ARCHIVO COMP #0 JEQ ENDFIL SALE SI ENCONTRO EL FIN DE ARCHIVO WRBUFF 05,BUFFER,LENGTH ESCRIBE EL REGISTRO EN LA SALIDA J CLOOP CICLO ENDFIL WRBUFF 05,EOF,THREE INSERTA MARCA DE FIN DE ARCHIVO J @RETADR EOF BYTE C’EOF’ THREE WORD 3 RETADR RESW 1 LENGTH RESW 1 LONGITUD DEL REGISTRO BUFFER RESB 4096 AREA DE BUFFER DE 4096 BYTES END FIRST FIGURA 4.1 Uso de macros en un programa 5 180 190 190a 190b 190c 190d 190d 190e 190f 190g 190h 190 i 190j 190k 1901 195 200 205 210 210a 210b 210c 210d 210e 210f 210g 210h 215 220 220a 220b 220c 220d 220e 220f 220g 220h 225 230 235 240 245 250 255 COPY FIRST .CL00P CL00P .ENDFIL ENDFIL EOF THREE RETADR LENGTH BUFFER START STL RDBUFF CLEAR CLEAR CLEAR + LDT TD JEQ RD C0MPR JEQ STCH TIXR JLT STX LDA C0MP JEQ WRBUFF CLEAR LDT LDCH TD JEQ WD TIXR JLT J WRBUFF CLEAR LDT LDCH TD JEQ WD TIXR JLT J BYTE WORD RESW RESW RESB END 0 RETADR X A S #4096 =X'F1' *-3 =X' F1' A,S *+11 BUFFER,X T *-19 LENGTH LENGTH #0 ENDFIL X LENGTH BUFFER,X =X'05' *-3 =X'05' T *-14 CL00P 05,EOF,THREE X THREEE E0F,X =X '05' *-3 =X '05' T *-14 @RETADR C'EOF' 3 1 1 4096 FIRST COPIA EL ARCHIVO DE LA ENTRADA EN LA SALIDA GUARDA LA DIRECCION DE RETORNO FI,BUFFER,LENGTH LEE EL REGISTRO DE ENTRADA EN EL BUFFER LIMPIA EL CONTADOR DE CICLO ASIGNA LA LONGITUD MAXIMA DEL REGISTRO PRUEBA EL DISPOSITIVO DE ENTRADA REPITE EL CICLO HASTA QUE ESTE LISTO LEE EL CARACTER EN EL REGISTRO A EXAMINA SI HAY FIN DE REGISTRO SALE DEL CICLO SI ES FIN DE REGISTRO ALMACENA EL CARACTER EN EL BUFFER REPITE EL CICLO A MENOS QUE SE HAYA ALCANZADO LA LONGITUD MAXIMA GUARDA LA LONGITUD DEL REGISTRO VERIFICA SI ES FIN DE ARCHIVO SALE SI ENCONTRO EL FIN DE ARCHIVO 05,BUFFER,LENGTH ESCRIBE EL REGISTRO EN LA SALIDA LIMPIA EL CONTADOR DE CICLO TOMA EL CARACTER DEL BUFFER PRUEBA EL DISPOSITIVO DE SALIDA REPITE EL CICLO HASTA QUE ESTE LISTO ESCRIBE EL CARÁCTER REPITE EL CICLO HASTA QUE SE HAYAN ESCRITO TODOS LOS CARACTERES CICLO INSERTA MARCA DE FIN DE ARCHIVO LIMPIA EL CONTADOR DE CICLO TOMA EL CARACTER DEL BUFFER PRUEBA EL DISPOSITIVO DE SALIDA REPITE EL CICLO HASTA QUE ESTE LISTO ESCRIBE EL CARÁCTER REPITE EL CICLO HASTA QUE SE HAYAN ESCRITO TODOS LOS CARACTERES LONGITUD DEL REGISTRO AREA DE BUFFER DE 4096 BYTES FIGURA 4.2 Programa de figura 4.1 con macros expandidas Dos nuevas instrucciones para el ensamblador: • MACRO identifica el inicio de la definición de macros, • MEND (línea 95) marca el final de la definición de macros, • este lenguaje de macros, cada parámetro comienza con el carácter &, que facilita la sustitución de los parámetros durante la expansión de macros. • Una proposición de invocación a macros se suele denominar una macrollamada. Para evitar confusiones con la proposición de llamada utilizada en los procedimientos y subrutinas, es preferible usar el término invocación • El programa de la figura 4.1 podría proporcionarse como entrada a un procesador de macros; la figura 4.2 muestra la salida que se generaría. Entrada (4.1) Salida (4.2) • Los argumentos y los parámetros se asocian entre sí, de acuerdo con sus posiciones. • Las dos invocaciones de WRBUFF especifican argumentos distintos, por lo que producen expansiones distintas. • Las proposiciones de invocación a macros se tratarán como comentarios, y las instrucciones generadas de las expansiones de macros se ensamblarán igual que si el programador las hubiera escrito directamente. • Las macroinstrucciones se han escrito para que el cuerpo de la macro no contenga etiquetas. • Para evitar la duplicación de símbolos se han eliminado las etiquetas del cuerpo de definición de estas macros. • "JLT *-14" práctica de programación pobre. Tablas y lógica del procesador de macros Procesador de macros de dos pasos: 1. Procesar las definiciones de macros 2. Las proposiciones de invocación a macros se expanden durante el segundo paso. • No permite que el cuerpo de una macroinstrucción contenga definiciones de otras macros 1 2 3 4 MACROS RDUFF WRBUFF 5 6 1 2 3 4 5 6 MACROX RDUFF WRBUFF MACRO MACRO . . . MEND MACRO . . . MEND . . . MEND MACRO MACRO . . . MEND MACRO . . . MEND . . MEND {Define las macros para la versión estándar de SIC} &INDEV,&BUFADR,&RECLTH {Versión estándar de SIC} {Fin de RDBUFF} &OUTDEV, &BUFADR, &RECLTH {Versión estándar de SIC} {Fin de WRBUFF} {Fin de MACROS} (a) {Define las macros para SIC/XE} &INDEV,&BUFADR,&RECLTH {Versión SIC/XE} {Fin de RDBUFF} &OUTDEV,&BUFADR,&RECLTH {Versión SIC/XE} {Fin de WRBUFF} {Fin de MACROX} (b) . FIGURA 4.3 Ejemplo de la definición de macros en el cuerpo de un macro. Pueden ser útiles: • La primera macro (MACROS) contiene proposiciones que definen RDBUFF, WRBUFF para SIC estándar • (MACROX) define esas mismas macros para el sistema SIC/XE. • El mismo programa puede ejecutarse sobre una máquina SIC estándar o una SIC/XE. Programa 4.3 MACROS SIC estándar MACROX SIC / XE *La definición de MACROS o de MACROX no define RDBUFF ni las otras macroinstrucciones. • Un procesador de macros de un paso que pueda alternar entre la definición y la expansión de macros puede manejar macros como las de la figura 4.3 • la definición de una macro debe aparecer en el programa fuente antes de cualquier proposición que invoque a la macro. Estructuras de datos básicas implicadas en este procesador de macros. 1. TABDEF (tabla de definiciones ), se almacenan las definiciones de macros y las proposiciones que constituyen el cuerpo de la macro. 2. TABNOM, para cada macroinstrucción definida, contiene apuntadores al inicio y al final de la definición en TABDEF. Sirve de índice para TABDEF. 3. (TABARG) que se utiliza durante la expansión de las invocaciones a macros. FIGURA 4.4 Contenido de las tablas del procesador de macros para el programa de la figura 4.1: (a) entradas de TABNOM y TABDEF que definen la macro RDBUFF, (b) entradas de TABARG para la invocación de RDBUFF en la línea 190. Sustitución de los argumentos • Para los parámetros se ha utilizado la notación posicional: el parámetro &INDEV se ha convertido en ?1 (que indica el primer parámetro del prototipo), &BUFAJDR se ha convertido en ?2, y así sucesivamente. • Cuando se reconoce la notación ?n, en una línea de TABDEF, una simple operación de indización proporciona el argumento apropiado de TABARG Algoritmo de un procesador de macros de un paso FIGURA 4.5 comienza {procesador de macros} EXPANSION := FALSO mientras CODOP < > 'END' haz comienza TOMA-LINEA PROCESA-LINEA termina {mientras} termina {procesador de macros} procedimiento PROCESA-LINEA comienza busca CODOP en TABNOM si lo encuentra entonces EXPANDE de otro modo si CODOP = 'MACRO' entonces DEFINE de otro modo describe la línea fuente en el archivo expandido termina {PROCESA-LINEA} procedimiento DEFINE comienza introduce el nombre de la macro en TABNOM introduce el prototipo de la macro en TABDEF NIVEL := 1 mientras NIVEL > 0 haz comienza TOMA-LINEA si no es una línea de comentario entonces comienza sustituye la notación posicional por parámetros introduce la línea en TABDEF si CODOP = 'MACRO' entonces NIVEL := NIVEL + 1 de otro modo si CODOP = 'MEND' entonces NIVEL := NIVEL - 1 termina {si no es comentario} termina {mientras} guarda en TABNOM apuntadores al principio y al final de la definición termina {DEFINE} procedimiento EXPANDE comienza EXPANSION := VERDADERO toma la primera línea de la definición de macros {prototipo} de TABDEF asigna los argumentos de la invocación a macros en TABARG escribe la invocación a macros en el archivo expandido como comentario mientras no se termine la definición de macros haz comienza TOMA-LINEA PROCESA-LINEA termina {mientras) EXPANSION := FALSO termina {EXPANDE) procedimiento TOMA-LINEA comienza si EXPANSION entonces comienza toma la siguiente línea de la definición de macros en TABDEF sustituye los argumentos de TABARG por notación posicional termina {si} de otro modo lee la siguiente línea del archivo de entrada termina {TOMA-LINEA) termina {TOMA-LINEA} • DEFINE, se llama al reconocer el inicio de una definición de macros, hace las entradas apropiadas en TABDEF y TABNOM. • EXPANDE coloca los valores de los argumentos en TABARG y expande la proposición de invocación a macros. • TOMA-LINEA, se llama en varios puntos del algoritmo, toma la siguiente línea que se va a procesar, y que puede proceder de TABDEF • DEFINE tiene un contador llamado NIVEL, cuyo valor se incrementa en uno cada vez que se lee una proposición MACRO, y disminuye en uno su valor cada vez que se lee una proposición MEND como (para compaginar MACRO-END). Por el ej. 4.3 • La mayoría de los procesadores de macros admiten la presencia de las definiciones de macros más usadas en la biblioteca estándar del sistema. Características del procesador de macros independientes de la máquina • Las características extendidas no están directamente relacionadas con la arquitectura del computador. 1. Concatenación de parámetros 2. Generación de etiquetas únicas 3. Expansión de macros condicional Concatenación de parámetros • Suponga series de variables: ▫ XA1, XA2, XA3, ..., otra serie por XB1, XB2, XB3, ... • El parámetro de la macroinstrucción podría especificar las series de variables con que se operará (A, B, etc.). • El procesador de macros utilizaría este parámetro para construir los símbolos requeridos en la expansión de macros (XA1, XB1, etc.). • LDA X&ID1 ¿Cómo reconocer hasta dónde termina el parámetro? • LDA X&ID—»1 Generación de etiquetas únicas • En general el cuerpo de una macroinstrucción no puede tener etiquetas del tipo usual. • Por ejemplo, WRBUFF de la figura 4.1. Si se colocara una etiqueta en la instrucción TD de la línea 135, esta etiqueta se definiría dos veces. • Muchos procesadores de macros evitan esos problemas mediante la creación de tipos especiales de etiqueta dentro de las macroinstrucciones. Propuesta • Las etiquetas utilizadas en el cuerpo de la macro comienzan con el carácter especial $ • En la figura 4.7 (b) cada símbolo que empieza con $ se ha modificado reemplazándolo por $AA ($XX siendo XX alfanumérico) • Se tienen hasta 1296 (36^2) expansiones de macros en un sólo programa. generación de etiquetas únicas 25 RDBUFF MACRO 30 CLEAR 35 CLEAR 40 CLEAR 45 +LDT 50 $LOOP TD 55 JEQ 60 RD 65 C0MPR 70 JEQ 75 STCH 80 TIXR 85 JLT 90 $EXIT STX 95 MEND RDBUFF CLEAR CLEAR CLEAR +LDT 30 35 40 45 50 $AAL00P 55 JEQ 60 RD 65 COMPRN 70 JEQ 75 STCH 80 TIXR 85 JLT 90 $AAEXIT STX 95 MEND &INDEV,&BUFADR,&RECLTH X LIMPIA EL CONTADOR DE CICLO A S #4096 ASIGNA LA LONGITUD MAXIMA DEL REGISTRO =X'&INDEV' PRUEBA EL DISPOSITIVO DE ENTRADA $L00P REPITE EL CICLO HASTA QUE ESTE LISTO -X'&INDEV" LEE EL CARACTER EN EL REGISTRO A A,S EXAMINA SI HAY FIN DE REGISTRO $EXIT SALE DEL CICLO SI ES FIN DE REGISTRO &BUFADR,X ALMACENA EL CARACTER EN EL BUFFER T REPITE EL CICLO A MENOS QUE SE HAYA $L00P ALCANZADO LA LONGITUD MAXIMA &RECLTH GUARDA LA LONGITUD DEL REGISTRO (a) FL,BUFFER,LENGTH X LIMPIA EL CONTADOR DE CICLO A S #4096 ASIGNA LA LONGITUD MAXIMA DEL REGISTRO TD =X'F1' PRUEBA EL DISPOSITIVO DE ENTRADA $AAL00P REPITE EL CICLO HASTA QUE ESTE LISTO =X'FL' LEE EL CARACTER EN EL REGISTRO A A,S EXAMINA SI HAY FIN DE REGISTRO $AAEXIT SALE DEL CICLO SI ES FIN DE REGISTRO &BUFFER,X ALMACENA EL CARACTER EN EL BUFFER T REPITE EL CICLO A MENOS QUE SE HAYA. $AAL00P ALCANZADO LA LONGITUD MAXIMA LENGTH GUARDA LA LONGITUD DEL REGISTRO (b) FIGURA 4.7 Generación de etiquetas únicas en la expansión de macros. Expansión de macros condicional • En esta sección se presenta un conjunto típico de proposiciones de expansión de macros condicional. • Figura 4.8. &E0R, especifica un código de caracter hexadecimal que marca el final de un registro, y &MAXLTH, que especifica la longitud máxima de registro que se puede leer. • (Como se verá más adelante, es posible omitir cualquiera de los dos parámetros en una invocación de REDBUFF.) • Las proposiciones de las líneas 44 a 48 de esta definición ilustran una estructura condicional (IF) • La figura 4.8(b-d) muestra la expansión de tres diferentes proposiciones de invocación a macros que ilustran la operación de las proposiciones IF de la figura 4.8(a). 25 26 27 28 30 35 38 40 42 43 44 45 46 47 48 50 55 60 63 65 70 73 75 80 85 90 95 RDBUFF IF $E0RCK ENDIF CLEAR CLEAR IF LDCH RMO ENDIF IF +LDT ELSE +LDT ENDIF $LOOP TD JEQ RD IF COMPR JEQ ENDIF STCH TIXR JLT $EXIT STX MEND MACRO &INDEV,&BUFADR,&RECLTH,&EOR,&MAXLTH (&E0R NE ") SET 1 X LIMPIA EL CONTADOR DEL CICLO A (&EOR EQ 1) =X'&E0R' ASIGNA EL CARACTER DE FIN DE REGISTRO A,S (&MAXLTH EQ ") #4096 HACE LA LONGITUD MAXIMA = 4096 # &MAXLTH ASIGNA LA LONGITUD MAXIMA DEL REGISTRO =X'&INDEV' PRUEBA EL DISPOSITIVO DE ENTRADA $L00P REPITE EL CICLO HASTA QUE ESTE LISTO -X'&INDEV' LEE EL CARACTER EN EL REGISTRO A (&E0R EQ 1) A,S EXAMINA SI HAY FIN DE REGISTRO $EXIT SALE DEL CICLO SI ES FIN DE REGISTRO &BUFADR,X T $LOOP &RECLTH (a) ALMACENA EL CARACTER EN EL BUFFER REPITE EL CICLO A MENOS QUE SE HAYA ALCANZADO LA LONGITUD MAXIMA GUARDA LA LONGITUD DEL REGISTRO Uso de proposiciones condicionales en el procesamiento de macros RDBUFF F3,BUF,RECL,04,2048 30 CLEAR 35 CLEAR 40 LDCH 42 RMO 47 +LDT 50 $AALOOP 55 JEQ 60 RD 65 COMPR 70 JEQ 75 STCH 80 TIXR 85 JLT 90 $AAEXIT X A =X'04' A,S #2048 TD $AAL00P =X'F3' A,S $AAEXIT $BUF,X T $AAL00P STX (b) LIMPIA EL CONTADOR DE CICL0 ASIGNA EL CARACTER DE FIN DE REGISTRO ASIGNA LA LONGITUD MAXIMA DEL REGISTRO =X'F3' PRUEBA EL DISPOSITIVO DE ENTRADA REPITE EL CICLO HASTA QUE ESTE LISTO LEE EL CARACTER EN EL REGISTRO A EXAMINA SI HAY FIN DE REGISTRO SALE DEL CICLO SI ES FIN DE REGISTRO ALMACENA EL CARACTER EN EL BUFFER REPITE EL CICLO A MENOS QUE SE HAYA ALCANZADO LA LONGITUD MAXIMA RECL GUARDA LA LONGITUD DEL REGISTRO (c) (c) RDBUFF 0E,BUFFER,LENGTH ,,80 30 CLEAR X 35 CLEAR A 47 +LDT #80 TD =X'0E' 55 JEQ $ABL00P 60 RD =X'0E' 75 STCH BUFFER,X ALMACENA EL CARACTER EN EL BUFFER 80 TIXR T 87 JLT $ABL00P REPITE EL CICLO A MENOS QUE SE HAYA ALCANZADO LA LONGITUD MAXIMA STX LENGTH GUARDA LA LONGITUD DEL REGISTRO 50 90 $ABL00P $ABEXIT LIMPIA EL CONTADOR DE CICLO ASIGNA LA LONGITUD MAXIMA DEL REGISTRO PRUEBA EL DISPOSITIVO DE ENTRADA REPITE EL CICLO HASTA QUE ESTE LISTO LEE EL CARACTER EN EL REGISTRO A (d) (d) 30 RDBUFF F1,BUFF,RLENG ,04 CLEAR X 35 40 42 45 CLEAR LDCH RM0 +LDT 50 55 60 65 70 75 80 85 90 $ACL00P TD JEQ RD C0MPR JEQ STCH TIXR JLT $ACEXIT STX A ' =X'04' A,S #4096 =X/F1 ' $ACL00P =X'F1' A,S $ACEXIT &BUFF,X T $ACL00P RLENG LIMPIA EL CONTADOR DE CICLO ASIGNA EL CARACTER DE FIN DE REGISTRO ASIGNA LA LONGITUD MAXIMA DEL REGISTRO = 4096 PRUEBA EL DISPOSITIVO DE ENTRADA REPITE EL CICLO HASTA QUE ESTE LISTO LEE EL CARACTER EN EL REGISTRO A EXAMINA SI HAY FIN DE REGISTRO SALE DEL CICLO SI ES FIN DE REGISTRO ALMACENA EL CARACTER EN EL BUFFER REPITE EL CICLO A MENOS QUE SE HAYA ALCANZADO LA LONGITUD MAXIMA GUARDA LA LONGITUD DEL REGISTRO • El procesador de macros debe mantener una tabla de símbolos que contenga los valores de todas las variables utilizadas en el momento del procesamiento. • La prueba de expresiones booleanas en las proposiciones IF se produce en el momento en que se expanden las macros. Uso de proposiciones de ciclo en el momento del procesamiento de macros 25 27 30 35 45 50 55 60 63 64 65 70 71 73 75 80 85 90 100 RDBUFF $E0RCT $LOOP &CTR &CTR $EXIT MACRO SET CLEAR CLEAR +LDT TD JEQ RD SET WHILE COMP JEQ SET ENDW STCH TIXR JLT STX MEND &INDEV,8tBUFADR,&RECLTH,&E0R %NITEMS(&EOR) X LIMPIA EL CONTADOR DE CICLO A #4096 HACE LA LONGITUD MAXIMA = 4096 -X'&INDEV' PRUEBA EL DISPOSITIVO DE ENTRADA $L00P REPITE EL CICLO HASTA QUE ESTE LISTO =X'&INDEV' LEE EL CARACTER EN EL REGISTRO A 1 (&CTR LE &E0R) =X'0000&E0R[&CTR]' $EXIT &CTR+1 &BUFADR,X T $LOOP &RECLTH (a) ALMACENA EL CARACTER EN EL BUFFER REPITE EL CICLO A MENOS QUE SE HAYA ALCANZADO LA LONGITUD MAXIMA GUARDA LA LONGITUD DEL REGISTRO (b) RDBUFF F2,BUFFER,LENGTH,(00,03,04) 30 CLEAR X 35 45 50 55 60 65 70 65 70 65 70 75 80 85 90 CLEAR +LDT TD JEQ RD COMP JEQ COMP JEQ COMP JEQ STCH TIXR JLT STX A #4096 HACE LA LONGITUD MAXIMA = 4096 =X'F2' PRUEBA EL DISPOSITIVO DE ENTRADA $AALOOP REPITE EL CICLO HASTA QUE ESTE LISTO =X'F2' LEE EL CARACTER EN EL REGISTRO A =X'000000' $SAAEXIT =X'000003' $AAEXIT =X'000004' $AAEXIT BUFFER,X ALMACENA EL CARACTER EN EL BUFFER T REPITE EL CJCLO A MENOS QUE SE HAYA $AALOOP ALCANZADO LA LONGITUD MAXIMA LENGTH GUARDA LA LONGITUD DEL REGISTRO $AALOOP $AAEXIT LIMPIA EL CONTADOR DE CICLO • con esta definición el programador puede especificar una lista de caracteres de fin de registro. • P.e., en la proposición de invocación a macros de la figura 4.9(b), hay una lista (00,03,04) correspondiente al parámetro &EOR Parámetros de macros de palabras clave • Con los parámetros posicionales, el programador ha de procurar especificar los argumentos en el orden apropiado. • Si se va a omitir un argumento, la invocación debe contener un argumento nulo (ver figura 4.8.c) ▫ GENERA ,,DIRECT,,,,,,3. • parámetros de palabras clave, el valor de los argumentos se escribe con una palabra clave. ▫ GENERA TYPE=DIRECT,CHANNEL=3. • En el prototipo de macro, cada nombre de parámetro va seguido de un signo “=“ que identifica un parámetro de palabra clave. • Después del signo igual, se especifica un valor por omisión para algunos parámetros. • El parámetro tiene este valor por omisión si su nombre no aparece en la proposición de invocación a macros. Valores por omisión • Para el parámetro &INDEV es F1. Para el parámetro & BUFADR no hay valor por omisión. • Aquí los argumentos pueden aparecer en cualquier orden.