l5 - generación de código -...

61
1 12048 - J. Neira - Lección 5: Generación De Código 1. Introducción 2. Tipos de Código Intermedio 3. Declaraciones 4. Expresiones y Asignación 5. Estructuras de Control 6. Procedimientos y Funciones Lecturas: Scott, capítulo 9 Muchnick, capítulos 4, 6 Aho, capítulo 8 Fischer, capítulos 10, 11 , 12 , 13, 14 Holub, capítulo 6 Bennett, capítulo 4, 10

Upload: lemien

Post on 01-Mar-2018

224 views

Category:

Documents


1 download

TRANSCRIPT

Page 1: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

1 12048 - J. Neira -

Lección 5: Generación De Código

1.  Introducción 2.  Tipos de Código Intermedio 3.  Declaraciones 4.  Expresiones y Asignación 5.  Estructuras de Control 6.  Procedimientos y Funciones

Lecturas: Scott, capítulo 9 Muchnick, capítulos 4, 6

Aho, capítulo 8 Fischer, capítulos 10, 11 , 12 , 13, 14 Holub, capítulo 6 Bennett, capítulo 4, 10

Page 2: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

2 12048 - J. Neira -

1/6. Introducción •  Se busca:

–  transportabilidad –  posibilidades de optimización

•  Debe ser: –  abstracto –  sencillo

•  No se tiene en cuenta: – modos de direccionamiento –  tamaños de datos –  existencia de registros –  eficiencia de cada operación

¿por qué no generar el código final directamente?

•  Código intermedio: interfaz entre ‘front-ends’ y ‘back-ends’

Page 3: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

3 12048 - J. Neira -

Código Intermedio •  Ventajas:

– Permite abstraer la má-quina, separar operacio-nes de alto nivel de su implementación a bajo nivel.

– Permite la reutilización de los front-ends y back-ends.

– Permite optimizaciones generales.

•  Desventajas: – Implica una pasada

más para el compilador (no se puede utilizar el modelo de una pasada, conceptualmente sim-ple).

– Dificulta llevar a cabo optimizaciones especí-ficas de la arquitectura destino.

– Suele ser ortogonal a la máquina destino, la tra-ducción a una arquitec-tura específica será más larga e ineficiente.

Page 4: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

4 12048 - J. Neira -

2/6. Tipos de Código Intermedio •  AST (Abstract Syntax

Trees): forma condensada de árboles de análisis, con sólo nodos semánticos y sin nodos para símbolos terminales (se supone que el programa es sintáctica-mente correcto).

•  Ventajas: unificación de pasos de compilación

– Creación del árbol y la tabla de símbolos

–  Análisis semántico – Optimización – Generación de código objeto

•  Desventaja: –  espacio para almacenamiento

E

‘+’ T id(A)

‘*’ id(C) id(B)

AST: Arbol de análisis:

E

T ‘+’

T

P

id(A)

P opmul P

id(B) id(C)

opad

‘*’

Page 5: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

5 12048 - J. Neira -

ASTs program gcd(input, output); var i,j : integer; begin

read(i,j); while i <> j do if i > j then i := i – j else j := j – i; writeln(i);

end.

Page 6: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

6 12048 - J. Neira -

Tipos de Código Intermedio •  DAG (Directed Acyclic Graphs): árboles sintácticos

concisos

– Ahorran algo de espacio – Resaltan operaciones duplicadas en el código – Difíciles de construir

árbol sintáctico:

E

‘+’ T

‘*’ id(C) id(B) ‘*’ id(C) id(B)

T

DAG: E

‘+’

T

‘*’ id(C) id(B)

Page 7: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

7 12048 - J. Neira -

Tipos de Código Intermedio •  TAC (Three-Address

Code): secuencia de instrucciones de la forma:

–  operador: aritmético / lógico –  operandos/resultado:

constantes, nombres, temporales.

•  Se corresponde con ins-trucciones del tipo:

•  Las operaciones más com-plejas requieren varias ins-trucciones:

•  Este ‘desenrollado’ facilita la optimización y genera-ción de código final. resultado := operando1 op operando2

a := b + c

(a + b) x (c – (d / e))

dir 1 dir 2 dir 3

Page 8: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

8 12048 - J. Neira -

TAC •  Ensamblador general y simplificado

para una máquina virtual: incluye etiquetas, instrucciones de flujo de control…

•  Incluye referencias explícitas a las direcciones de los resultados intermedios (se les da nombre).

•  La utilización de nombres permite la reorganización (hasta cierto punto).

•  Algunos compiladores generan este código como código final; se puede interpretar fácilmente (UCSD PCODE, Java).

•  Operadores: CI generación optimización

corto compleja compleja muchos

pocos largo sencilla sencilla

Page 9: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

9 12048 - J. Neira -

TAC •  Variaciones sintácticas:

(Fischer)

(READI, A) (READI, B) (GT, A, B, t1) (JUMP0, t1, L1) (ADDI, A, 5, C) (JUMP, L2) (LABEL, L1) (ADDI, B, 5, C) (LABEL, L2) (SUBI,C, 1, t2) (MULTI, 2, t2, t3) (WRITEI, t3)

(Aho) 1. Asignación:

x := y op z x := op y x := y x[i] := y x := y[i] x := &y x := *y *x := y

2. Saltos: goto L if x oprel y goto L

3. Procedimientos: param x1 ... param xn call p, n

Page 10: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

10 12048 - J. Neira -

Representaciones de TAC

•  Cuádruplas: el destino suele ser una temporal.

•  Tripletas: sólo se repre-sentan los operandos

•  Supuesta ventaja: es más concisa.

•  Desventaja: el código ge-nerado es dependiente de la posición.

Cierto: la dependencia posi- cional dificulta la optimización.

Falso: estadísticamente se requieren más instrucciones. (*, b, c, t1)

(*, b, d, t2) (+, t1, t2, a)

(*, b, c) (*, b, d) (+, (1), (2)) (:=, (3), a)

(1) (2) (3) (4)

a := b * c + b * d; Fuente:

Page 11: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

11 12048 - J. Neira -

Representaciones de TAC •  Tripletas Indirectas: + vector que indica el orden de

ejecución de las instrucciones.

Reorganizar es eficiente

Se puede com- partir espacio

b * c b * d b * c (1) + (2) (4) * (3) a := (5);

1 2 3 4 5 6

b * d b * c b * c (1) + (2) (4) * (3) a := (5);

2 1 3 4 5 6

b * c b * d (1) + (2) (3) * (1) a := (4);

1 2 3 4 5

a := (b * c + b * d) * b * c;

Page 12: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

12 12048 - J. Neira -

RTL: register transfer language d = (a + b) * c;

Page 13: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

13 12048 - J. Neira -

Notación posfija •  Polaca inversa, código de cero direcciones:

– notación matemática libre de paréntesis – los operadores aparecen después de los operandos

a := b * c + b * c

@a b c mult b c mult add asg

Expresiones:

1. E átomo ⇒ E ’

2. E1 op E2 ⇒ E1’ E2’ op

3. (E) ⇒ E’

Asignación:

id := E ⇒ @id E’ asg

Page 14: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

14 12048 - J. Neira -

Notación Postfija •  Ventajas:

– Código generado conciso. – No hacen falta temporales. –  Algunas optimizaciones

sencillas. – Mantiene la estructura

sintáctica.

•  Desventajas: – Código dependiente de la

posición. –  solo efectiva si el ‘target’ es

de pila.

@a b c mult dup add asg

a := b * c + b * c

a + b * c (a + b) * c

E

‘+’ T id(A)

‘*’ id(C) id(B)

E

‘*’ T id(C)

‘+’ id(B) id(A)

a b c mult add

a b add c mult

Page 15: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

15 12048 - J. Neira -

Generación de código intermedio •  Consideración fundamental: generación de código

correcto.

•  Sin hacerse estas preguntas, es razonablemente sencillo.

a := b * c

; Dirección de A. SRF 0 5 ; Acceso a B. SRF 0 4 DRF ; Acceso a C. SRF 0 3 DRF TMS ; Asignación. ASG

INEFICIENCIA EN TIEMPO:

¿hay alguna forma menos costosa de hacer la multiplicación?

INEFICIENCIA EN ESPACIO:

¿está b * c calculado en algún sitio?

Page 16: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

16 12048 - J. Neira -

3/6. Procesamiento de declaraciones

•  no se genera código (hay excepciones).

•  se limita a resolver proble-mas relacionados con al-macenamiento de los obje-tos:

–  Espacio requerido –  Lugar en la memoria –  Valor

•  hay información explícita e implícita en el fuente.

•  Declaración de variables: Esencialmente se trata de completar

la tabla de símbolos int sig, nivel = 0; void abrir_bloque() { ... sig = INICIAL; ++nivel; } void cerrar_bloque() { ... nivel--; } void crear_var (char *nom, int tipo) { ..... simbolo->dir = sig; switch (tipo) { case ENTERO : sig += 2; break; case REAL : sig += 4; break; .... } } Al final, sig indica el tamaño

del bloque de activación.

Page 17: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

17 12048 - J. Neira -

Ejemplo Programa p; entero i, j, m;

accion dato (ref entero d); Principio Fin

accion mcd(Val entero a, b; ref entero m); entero r;

Principio Fin

Principio Fin

3 4 5

3

3 4 5

6

Page 18: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

18 12048 - J. Neira -

Declaración de Variables •  ¿Y si se permite mezclar

declaraciones de variables y procedimientos?

•  ¿Y si necesitas mantener información sobre el tama-ño de cada bloque?

•  C: este problema no existe. •  Pascal: muchos compilado-

res lo prohíben.

•  Posible solución: procedure P; var i,j,k : integer;

procedure Q; var l,m : integer; begin .... end;

var n : integer;

i.dir = 0 j.dir = 2 k.dir = 4

l.dir = 0 m.dir = 2

n.dir = 4 (¡igual que k!)

int sig[MAXANID], nivel = 0;

void abrir_bloque () {... sig[++nivel] = INICIAL;}

void cerrar_bloque () { ... nivel--;}

void crear_var (char *nom, int tipo) { .... simbolo->dir = sig[nivel]; ... }

Page 19: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

19 12048 - J. Neira -

Inicializadores, C: •  extern y static:

–  Valor inicial por defecto: 0. –  Admiten sólo valores

constantes. –  El inicializador se ejecuta una

sola vez.

•  auto y struct: –  Valor inicial por defecto:

ninguno. –  Admiten valores no

constantes. –  Se ejecutan c/vez que se

activa el bloque. #include <stdio.h> /* ¿legal? */ int i = 1, /* ¿legal? */ j = i + 1, /* ¿legal? */ m = 34 + 1, f(), /* ¿legal? */ k = f(), /* ¿legal? */ l;

/* ¿legal? */ extern int n = 0;

int f() { /* ¿legal? */ int i = 1, /* ¿legal? */ j = i + 1, g(), /* ¿legal? */ k = g(i), /* ¿legal? */ n = f(), l;

/* ¿legal? */ static int m = 1; ..... }

Page 20: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

20 12048 - J. Neira -

Esquema general, secuencial

programa p; ... principio ... fin

%union {... char *cadena;... } ...

programa: tPROGRAMA tIDENTIFICADOR ';' { inicio_generacion_codigo (); $<cadena>$ = nueva_etiqueta (); generar (ENP, $<cadena>$); } declaracion_variables declaracion_acciones { comentario (sprintf(msg, "Comienzo de %s", $2.nombre)); etiqueta($<cadena>4); } bloque_instrucciones { comentario (sprintf(msg, "Fin de %s", $2.nombre)); generar (LVP); fin_generacion_codigo(); }

ENP L0 ... ; Comienzo de p L0: ... ; Fin de p LVP

Page 21: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

21 12048 - J. Neira -

Esquema general, AST

programa p; ... principio ... fin

%union {... LISTA cod; } ... %type <cod> bloque_instrucciones %type <cod> declaracion_acciones

ENP L0 ... ; Comienzo de p L0: ... ; Fin de p LVP

programa: tPROGRAMA tIDENTIFICADOR ';' declaracion_variables declaracion_acciones bloque_instrucciones { char *lenp = newlabel(), msg[100];

$$ = code (ENP, lenp); concatenar (&($$), $5); sprintf(msg, "Comienzo de %s“,...); comment (&($$), msg); label(&($$), lenp); concatenar (&($$), $6); sprintf(msg, "Fin de %s",...); comment (&($$), msg); emit (&($$), LVP); dumpcode ($$, fich_sal); }

Page 22: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

22 12048 - J. Neira -

4/6. Expresiones y Asignación

•  De los operandos: – Determinar su localización –  Efectuar conversiones

implícitas

•  De los operadores: – Respetar su precedencia – Respetar su asociatividad – Respetar orden de evaluación

(si definido) – Determinar interpretación

correcta (si sobrecargado)

•  Instrucciones generadas –  Acceso a datos

»  Variables simples » Registros »  Vectores

– Manipulación de datos » Conversiones » Operaciones

–  Flujo de control »  Validación de subrangos » Operadores complejos

x[i, j] := a*b + c*d - e*f + 10;

Page 23: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

23 12048 - J. Neira -

Algunas dificultades •  Orden de evaluación de los

operandos: •  Método de evaluación de

los operadores:

a[i] = i++; ¿el valor del subíndice es el anterior o actual valor de i?

FRAMES[pop()] = pop(); ¿Corresponde a ASG o ASGI?

push(pop() - pop());

¿Implementa correctamente SBT? ¿Es relevante en el caso de PLUS?

En C, ni la suma ni la asignación tienen predefinido un orden de evaluación.

push (pop() and pop());

¿Implementa AND correctamente en PASCAL?

push (pop() && pop());

¿Implementa AND correctamente en C?

En C, el operador && se evalúa por corto circuito y por lo

tanto de izquierda a derecha.

Page 24: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

24 12048 - J. Neira -

Operandos: acceso a nombres (sec) •  La información esencial debe obtenerse de la tabla

de símbolos. factor : TIDENT { generar (SRF, ?, ?); generar (DRF); /* ¿parametro? */ } | TIDENT { generar (SRF, ?, ?); /* ¿parametro? */ } '[' expresion ']' { /* ?tamano? */ generar (DRF); } | TIDENT '(' args ')' { generar (OSF, ?, ?, ?); } ..... ;

constante : TTRUE { generar (STC, 1); } | TFALSE { generar (STC, 0); } | TENTERO { generar (STC, $1); } | TCARACTER { generar (STC, $1); } ;

Page 25: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

25 12048 - J. Neira -

Operandos: acceso a nombres (AST) •  La información esencial debe obtenerse de la tabla

de símbolos. constante : TTRUE { $$.cod = code (STC, 1); } | TFALSE { $$.cod = code (STC, 0); } | TENTERO { $$.cod = code (STC, $1); } | TCARACTER { $$.cod = code (STC, $1); } ;

factor : TIDENT { $$.cod = code (SRF,?,?); emit (&($$.cod), DRF); /* ¿parametro? */ } | TIDENT '[' expresion ']' { $$.cod = code (SRF, ?, ?); /* ¿parametro? */ concatenar (&($$.cod), $3.cod); /* ?tamano? */ emit (&($$), (DRF); } | TIDENT '(' args ')' { $$.cod = $3; emit (&($$.cod),OSF,?,?,?); } ..... ;

Page 26: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

26 12048 - J. Neira -

Vectores •  Componentes almacenadas

de forma contigua

•  Vectores de dimensión defi-nida en compilación, des-plazamiento de V[i]:

•  En C:

•  se reduce a aritmética de punteros:

V[1] V[2] V[3] V[4] V[5]

(i – lim_inf) x tamaño

i x tamaño

v[i] es equivalente a

*(v + i)

Page 27: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

27 12048 - J. Neira -

Procesamiento de Vectores •  Dada var v : array[4..8] of integer;

v[<expresión1>] := <expresión2>;

; n y o dependen de la declaración SRF n o ; código para expresión1 ... ; límite inferior STC 4 SBT ; tamaño (en este caso sobra) STC 1 TMS PLUS ; código para expresión2 ... ASG

¿o sea que el límite superior no sirve?

Page 28: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

28 12048 - J. Neira -

Procesamiento de Vectores •  Dada var v : array[-3..5] of boolean;

if v[<expresión>] then ...;

; n y o dependen de la declaración SRF n o ; código para expresión ... ?? ?? STC -3 GTE JMF ... ; procedimiento de error STC 5 LTE JMF ... ; procedimiento de error ; límite inferior STC -3 SBT ; tamaño STC 1 TMS PLUS DRF JMF ...

¿qué hacer aquí?

Page 29: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

29 12048 - J. Neira -

Matrices contiguas por filas, v1

4

5

8

40

8

1 105 264

entero v[2..5,3..7,1..8];

.... v[2,3,1] := ...; v[5,7,8] := ...; v[3,4,5] := ...; ¿dirección?

105 157

105 105

159

52

0

Page 30: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

30 12048 - J. Neira -

Formulación alternativa, v2

4

5

8

entero v[2..5,3..7,1..8];

.... v[2,3,1] := ...; v[5,7,8] := ...; v[3,4,5] := ...;

¿dirección? 105

2

13

105

0

5

32

264

159

3

19

157

52

Page 31: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

31 12048 - J. Neira -

Matrices: generación de código, v2 factor : TIDENT { int nivel = ..., /* nivel sint. */ int offset = ....; /* dir en BA */

generar (SRF, nivel, offset); /* ¿par x ref? */ } '[' lista_indices ']’ { int t = ...; /* Tamaño elems */ int c = ...; /* Parte constante */

generar (STC, c); generar (SBT); generar (STC, t); generar (TMS); generar (PLUS); generar (DRF); } ;

cn

dn addr

Page 32: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

32 12048 - J. Neira -

Matrices: generación de código, v2 %union { ..... int i; ..... } %type <i> lista_indices %% lista_indices: expresion { $$ = 1; } | lista_indices ',' { int s_i, i;

i = $1 + 1; s_i = ..., generar (STC, s_i); generar (TMS); } expresion { generar (PLUS); $$ = $1 + 1; } ;

ei

e1

si

ci-1

ci-1 si

c1 = e1

ci = ci-1 si + ei

Page 33: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

33 12048 - J. Neira -

¿y porqué no...? {% int i; %} %% lista_indices: expresion { i = 1; } | lista_indices ',' { int s_i, i; i = i + 1; s_i = ..., generar (STC, s_i); generar (TMS); } expresion { generar (PLUS); } ;

ei

e1

si

ci-1

ci-1 si

c1 = e1

ci = ci-1 si + ei

entero v[1..10], w[1..3, 1..4, 1..5, 1..6]; .... w[v[1], v[2], v[3], v[4]] := ...;

Page 34: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

34 12048 - J. Neira -

Ejemplo: para v[3,4,5] ; v

SRF n o ; e_1

STC 3 ; s_ 2

STC 5 TMS

; e_2 STC 4 PLUS

; s_3 STC 8 TMS

; e_3 STC 5 PLUS

; fin de los indices ; c

STC 105 SBT PLUS

; v SRF n o

; e_1 STC 3

; m_1 STC 40 TMS PLUS

; e_2 STC 4

; m_2 STC 8 TMS PLUS

; e_3 STC 5

; m_3 STC 1 TMS PLUS

; fin de los indices ; c

STC 105 SBT

v1 v2

¿cuál es más eficiente?

Page 35: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

35 12048 - J. Neira -

Operadores •  Algoritmo recursivo: comenzando en la raíz del

árbol sintáctico: Para un operador n-ario:

1.  Generar código para eva-luar los operandos 1..n, al-macenando los resultados en localizaciones tempo-rales-

2.  Generar código para eva-luar el operador, utilizando los operandos almacena-dos en las n localizaciones temporales y almacenando el resultado en otra locali-zación temporal.

a*b + c*d - e*f + 10

10

+

-

+

*

a b

*

c d

*

e f

a b * c d * + e f * - 10 +

Page 36: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

36 12048 - J. Neira -

Operadores Aritméticos (sec) %union { ... int instr; ... } %type <instr> op_ad op_mul %% expr_simple : termino | '+' termino | '-' termino { generar (NGI); } | expr_simple op_ad termino { generar ($2); } ; op_ad : '+' { $$ = PLUS; } | '-' { $$ = SBT; } ; termino : factor | termino op_mul factor { generar ($2); } ; op_mul : '*' { $$ = TMS; } | TDIV { $$ = DIV; } | TMOD { $$ = MOD; } ;

Los operadores lógicos se tratan de forma similar, excepto....

Page 37: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

37 12048 - J. Neira -

Corto circuito: or else •  Implica operaciones de control de flujo:

A or else B if A then true else B

A JMT T B JMP Fin

T: STC 1 Fin:

A JMF F STC 1 JMP Fin

F: B Fin:

A v v f f B v f v f

Instr. a+2 a+2 a+b+2

a+b+2

A v v f f B v f v f

Instr. a+3 a+3 a+b+1

a+b+1

Page 38: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

38 12048 - J. Neira -

Corto circuito: and then

A and then B if A then B else false

A v v f f B v f v f

Instr.

A v v f f B v f v f

Instr.

A JMF F B JMP Fin

F: STC 0 Fin:

A JMT T STC 0 JMP Fin

T: B Fin:

Page 39: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

39 12048 - J. Neira -

Siguiente problema.... •  ¿qué hacer con los

resultados intermedios? •  Máquinas de pila:

Depende del tipo de código intermedio

a*1b +1 c*2d - e*3f +2 10

10

+

-

+

*

a b

*

c d

*

e f

;variable A SRF 0 3 DRF ;variable B SRF 0 4 DRF ;*1: A * B TMS ;variable C SRF 0 5 DRF ;variable D SRF 0 6 DRF ;*2:C * D TMS ;+1:(A*B)+(C*D) PLUS ;variable E SRF 0 7 DRF ;variable F SRF 0 8 DRF ;*3:E * F TMS ;-:((A*B)+(C*D))-(E*F) SBT STC 10 ;+2:(((A*B)+(C*D))-(E*F))+10 PLUS

Page 40: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

40 12048 - J. Neira -

TAC: Variables temporales •  Se supone disponible una cantidad ilimitada de variables

•  Al traducir este código intermedio para una arquitectura destino, se utilizarán registros en lo posible, de lo contrario posiciones de memoria.

t0 := A * B; t1 := C * D; t2 := t0 + t1; t3 := E * F; t4 := t2 - t3; t5 := t4 + 10;

a*1b +1 c*2d - e*3f +2 10

‘register allocation problem’

Page 41: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

41 12048 - J. Neira -

Código de tres direcciones •  Se utiliza un generador de nombres temporales:

•  Las expresiones tienen como atributo el nombre de la variable en la que quedan almacenadas. %{ extern char *newtemp(); %} %union {...char *place;...} %type <place> TIDENT expresion %type <place> expresion_simple termino factor

char *newtemp () { static int c = 0; char *m = malloc (5);

sprintf (m, "t%d", c++); return m; }

Page 42: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

42 12048 - J. Neira -

Código de tres direcciones expresion : simple { strcpy ($$, $1); } ; simple : termino { strcpy ($$, $1); } | '+' termino { strcpy ($$, $2);} | '-' termino { strcpy ($$, newtemp()); tac ("%s := -%s;\n",$$, $2); } | simple '+' termino { strcpy ($$, newtemp()); tac("%s := %s + %s;\n",$$, $1, $3); } | simple '-' termino { strcpy ($$, newtemp()); tac("%s := %s - %s;\n",$$, $1, $3); } ; factor : TIDENT { strcpy ($$, $1); } | '(' expresion ')‘ { strcpy ($$, $2); } | TENTERO { sprintf ($$, "%d", $1);} ;

Page 43: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

43 12048 - J. Neira -

Reutilización de temporales •  Una vez que una variable

temporal aparece como operando, deja de utilizar-se.

•  Al traducir el código inter-medio, en lo posible se uti-lizarán registros (habrá una cantidad limitada); de lo contrario, posiciones de memoria.

•  Reducción de temporales requeridas:

1.  c = 0

2.  Para generar un nuevo nombre temporal, utilizar tc, e incrementar c en 1.

3.  Cuando aparezca un nombre temporal como operando, decrementar c en 1.

t0 := A * B; t1 := C * D; t0 := t0 + t1; t1 := E * F; t0 := t0 - t1; t0 := t0 + 10;

0 1 2 1 2 1 1

t0 := A * B; t1 := C * D; t2 := t0 + t1; t3 := E * F; t4 := t2 - t3; t5 := t4 + 10;

Page 44: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

44 12048 - J. Neira -

5/6. Estructuras de Control •  Sin consideraciones de eficiencia, la generación de

código es relativamente sencilla: •  Ejemplo 1: repetir

<instr> hasta <exp>

INSTR: ; <instr> ; <exp> JMF INSTR

repetir: tREPETIR { $<instr>$ = nueva_etiqueta(); etiqueta ($<instr>$); } lista_instrucciones tHASTA_QUE expresion { generar (JMF, $<instr>2); } ;

Page 45: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

45 12048 - J. Neira -

Selección (sec)

si <exp> ent <instr1> si_no <instr2> fsi

seleccion: tSI expresion { $<sino>$ = nueva_etiqueta(); generar (JMF, $<sino>$); } tENT lista_instrucciones { $<fin>$ = nueva_etiqueta(); generar (JMP,$<fin>$); etiqueta ($<sino>3); } resto_seleccion tFSI { etiqueta($<fin>6); } ; resto_seleccion: | tSI_NO lista_instrucciones ;

; <exp> JMF SINO ; <instr1> JMP FIN SINO: ; <instr2> FIN:

Page 46: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

46 12048 - J. Neira -

Optimalidad •  La generación de código puede no ser óptima:

si i = 1 ent i := i + 1; fsi

; exp SRF n o DRF STC 1 EQ JMF L0 ; l1 SRF n o SRF n o DRF STC 1 PLUS ASG JMP L1 L0: L1:

Page 47: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

47 12048 - J. Neira -

Selección (AST) seleccion: tSI expresion tENT lista_instrucciones resto_seleccion tFSI { char *lsino = newlabel(), *lfin = newlabel();

$$ = $2.cod; emit (&($$), JMF, lsino); concatenar (&($$), $4); if (longitud_lista($5)) { emit (&($$), JMP, lfin); label (&($$), lsino); concatenar (&($$), $5); label (&($$), lfin); } else label (&($$), lsino); } ; resto_seleccion: { $$ = newcode();} | tSI_NO lista_instrucciones { $$ = $2};

; <exp> JMF SINO ; <instr1> SINO:

; <exp> JMF SINO ; <instr1> JMP FIN SINO: ; <instr2> FIN:

Page 48: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

48 12048 - J. Neira -

Selección múltiple

caso <exp> <exp1> : <instr1> ; ... <expn> : <instrn> ; dlc <instr> fcaso

; caso ; exp ; exp1 EQ JMF EXP2 ; instr1 JMP FIN EXP2: ... EXPn: ; expn EQ JMF DLC ; instrn JMP FIN DLC: ; dlc ; instr FIN:

¿problemas?

Page 49: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

49 12048 - J. Neira -

Selección múltiple

si <exp> = <exp1> ent <instr1> si_no si <exp> = <exp2> ent <instr2> .... si_no si <exp> = <expn> ent <instrn> si_no <instr> fsi ... fsi

equivale a:

; caso ; exp DUP ; exp1 EQ JMF EXP2 ; instr1 JMP FIN EXP2: ... EXPn: DUP ; expn EQ JMF DLC ; instrn JMP FIN DLC: ; dlc ; instr FIN: POP

Page 50: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

50 12048 - J. Neira -

Mientras que (sec)

mq <exp> hacer <instr> fmq

mientras_que: tMQ { $<exp>$ = nueva_etiqueta(); etiqueta ($<exp>$); } expresion { $<fin>$ = nueva_etiqueta(); generar (JMF, $<fin>$); } instr tFMQ { generar (JMP, $<exp>2); etiqueta($<fin>4); } ;

EXP: ; <exp> JMF FIN ; <instr> JMP EXP FIN:

Page 51: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

51 12048 - J. Neira -

Mientras que (AST)

mq <exp> hacer <bloque> fmq

mientras_que: tMQ expresion bloque tFMQ { char *lcond = newlabel(), *lbloque = newlabel();

$$ = code (JMP, lcond); label (&($$), lbloque); concatenar( &($$), $3); label (&($$), lcond); concatenar (&($$), $2); emit (&($$), JMT, lbloque); }

JMP COND BLOQUE: ; <bloque> COND: ; <exp> JMT BLOQUE

Page 52: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

52 12048 - J. Neira -

6/6. Procedimientos y Funciones

accion q (val entero i; ref booleano t); entero j; booleano f;

accion r (ref entero j); entero i; principio q (i, t); r (j) fin

principio q (j, f); r (i) fin

Declaraciones: • Recuperar los argumentos • Generar el código del procedimiento/función • Devolver el valor resultado (funciones)

Invocaciones: • Apilar los argumentos • Ejecutar la invocación

Page 53: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

53 12048 - J. Neira -

Argumentos •  Los argumentos se transmiten a través del stack

accion p(val entero i; ref booleano k; val caracter c); .......... p (a,b,d);

; apilar A ; apilar B ; apilar D ; invocar P OSF s l a

; recuperar C ; recuperar K ; recuperar I JMP P ... P: ; accion P ... CSF

Page 54: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

54 12048 - J. Neira -

Invocación de Procedimientos •  Cuando se evalúan las ex-

presiones correspondien-tes a los argumentos, éstos van almacenándose en la pila.

•  Al crear el BA del procedi-miento, debe respetarse el tamaño del bloque actual

•  El cambio de nivel es la diferencia entre el nivel actual y el invocado.

•  La dirección del procedi-miento o función se deter-mina al introducir el símbolo en la tabla.

SRF nn on DRF STC 1 PLUS SRF nb ob DRF SRF nc oc DRF STC 1 PLUS OSF s l a

p (n+1, b, entacar(c+1));

Page 55: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

55 12048 - J. Neira -

Invocación de Procedimientos •  Los parámetros ref requie-

ren la dirección de la varia-ble referenciada; expresion genera código para obtener el valor de la variable.

•  Para los parámetros ref elimino la última instruc-ción de código generado por expresion

SRF nn on DRF STC 1 PLUS SRF nb ob DRF SRF nc oc DRF STC 1 PLUS OSF s l a

n+1

b

entacar(c+1)

SRF nn on DRF STC 1 PLUS SRF nb ob

SRF nc oc DRF STC 1 PLUS OSF s l a

Page 56: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

56 12048 - J. Neira -

; accion Q ; recuperar args Q JMP Q ; accion R ; recuperar args R JMP R R: ; codigo de R CSF Q: ; código de Q CSF

Declaración de procedimientos •  Evitar el posible código

de procedimientos y funciones locales

accion q (...);

accion r (...); principio ... fin

principio ... fin

; accion Q ; recuperar args Q JMP Q ; accion R ; recuperar args R JMP R R: ; codigo de R CSF Q: ; código de Q CSF

; accion R ; recuperar args R R: ; codigo de R CSF ; accion Q ; recuperar args Q Q: ; código de Q CSF

Page 57: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

57 12048 - J. Neira -

Recuperar los argumentos •  Los parámetros por va-

lor/referencia se tratan de forma separada: – Todos se recuperan al

inicio, unos son valores y otros son direcciones

– Ninguno se devuelve al final.

•  Los parámetros por copia se tratan como variables locales: – Todos se recuperan al

inicio – Los que son S o E/S se

devuelven al final

•  Los argumentos de tipo vector pueden requerir que todas las compo-nentes sean almacena-das en la pila y luego recuperadas.

; recuperar C SRF 0 5 ASGI ; recuperar K SRF 0 4 ASGI ; recuperar I SRF 0 3 ASGI

Page 58: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

58 12048 - J. Neira -

Utilización de parámetros 1.  valor de un parámetro por

referencia 2.  dirección de un parámetro

por referencia 3.  valor de un parámetro por

valor y otro por referencia 4.  parámetro por valor utiliza-

do como argumento a parámetro por referencia

5.  parámetro por referencia utilizado como argumento a parámetro por referencia

6.  variables utilizadas como parámetros por valor y re-ferencia respectivamente

programa p; entero i, j;

accion q(ref entero m); principio escribir (m); m := 0 fin

accion r(val entero k; ref entero l); principio escribir (k, l); l := 0; q (k); q (l); fin

principio r (i, j); fin

1 2

3 4 5

6

Page 59: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

59 12048 - J. Neira -

Código que debe ser generado ENP L0 ; accion Q SRF 0 3 ;rec. M ASGI JMP L1 L1: SRF 0 3 ; M DRF DRF WRT 1 SRF 0 3 ; M DRF STC 0 ASG CSF ; accion R SRF 0 4 ;rec. L ASGI SRF 0 3 ;rec. K ASGI JMP L2 L2: SRF 0 3 ; K DRF WRT 1

SRF 0 4 ; L DRF DRF WRT 1 SRF 0 4 ; L DRF STC 0 ASG SRF 0 3 ; K OSF 5 1 1 ; Q SRF 0 4 ; L DRF OSF 5 1 1 ; Q CSF ; ppal P L0: SRF 0 3 ; I DRF SRF 0 4 ; J OSF 5 0 13 ; R LVP

1

2

3

4

5

6

3

Page 60: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

60 12048 - J. Neira -

Y para funciones..... •  Versión C:

funcion mcd( val entero a,b) dev entero; entero r; principio r := a mod b; mq r <> 0 a := b; b := r; r := a mod b fmq; dev (b); fin

; recuperar parametros SRF 0 4 ; B ASGI SRF 0 3 ; A ASGI JMP MCD ; codigo de mcd MCD: ... ... ; dejar resultado en ; la pila SRF 0 4 DRF CSF CSF

Page 61: L5 - Generación de código - webdiis.unizar.eswebdiis.unizar.es/~neira/12048/generaciondecodigo.pdf · 12048 - J. Neira - 3 Código Intermedio • Ventajas: – Permite abstraer

61 12048 - J. Neira -

Y para funciones..... •  Versión Pascal:

; recuperar parámetros SRF 0 5 ; B ASGI SRF 0 4 ; A ASGI JMP MCD ; código de mcd MCD: ... ... SRF 0 3 ; MCD SRF 0 5 ; B DRF ASG ; dejar resultado en ; la pila SRF 0 3 ; MCD DRF CSF

funcion mcd( val entero a, b) dev entero; entero r; principio r := a mod b; mq r <> 0 a := b; b := r; r := a mod b fmq; mcd := b; fin