etapas finales de un traductor

79
Etapas finales de un traductor M.C. Juan Carlos Olivares Rojas Noviembre 2009

Upload: vivian

Post on 15-Jan-2016

45 views

Category:

Documents


0 download

DESCRIPTION

Etapas finales de un traductor. M.C. Juan Carlos Olivares Rojas. Noviembre 2009. Agenda. Generador de código intermedio (opcional) Optimizador (puede ser opcional e ir en esta etapa o hasta después de haber generado la traducción) Generador de código objeto. Generación de Código Intermedio. - PowerPoint PPT Presentation

TRANSCRIPT

Page 1: Etapas finales de un traductor

Etapas finales de un traductor

M.C. Juan Carlos Olivares Rojas

Noviembre 2009

Page 2: Etapas finales de un traductor

Agenda• Generador de código intermedio

(opcional)

• Optimizador (puede ser opcional e ir en esta etapa o hasta después de haber generado la traducción)

• Generador de código objeto.

Page 3: Etapas finales de un traductor

Generación de Código Intermedio

Etapas Finales de un Traductor

Page 4: Etapas finales de un traductor

Agenda• Lenguajes intermedios.

• Notaciones. – Infija. – Postfija. – Prefija.

• Representación de código intermedio. – Notación Polaca. – Codigo P. – Triplos y Cuádruplos.

Page 5: Etapas finales de un traductor

Agenda• Esquemas de generación.

– Expresiones. – Declaración de variables, constantes – Estatuto de asignación. – Estatuto condicional. – Estatuto de ciclos – Arreglos. – Funciones.

Page 6: Etapas finales de un traductor

Código Intermedio• Es una etapa opcional en muchos casos

que ayuda a simplificar la producción de código objeto

• La administración de la memoria se da en esta etapa.

• Se debe considerar tanto la memoria estática como dinámica, y en esta se utilizan generalmente pilas.

Page 7: Etapas finales de un traductor

Generador de Cod. Intermedio• Los lenguajes intermedios generalmente

tienen árboles de derivación más pequeños que su contraparte original.

• Se puede representar un árbol sintáctico con un Grafo Dirigido Acíclico (GDA).

• La notación postfija es una manera linealizada de representar un árbol sintáctico.

Page 8: Etapas finales de un traductor

Generador Cod. Intermedio• a := b*-c+b*-c • abc -*bc -*+=

• x := y op z • x+y*z • t1:=y*z • t2:=x+t1

Page 9: Etapas finales de un traductor

Lenguajes intermedios• Los lenguajes intermedios nos sirven para

representar la producción final de nuestro lenguaje fuente.

• Existen muchos lenguajes intermedios, la mayoría de ellos son una representación más simplificada del código original para facilitar la traducción hacia el código final.

Page 10: Etapas finales de un traductor

Lenguajes Intermedios• Otros lenguajes intermedios sirven de

base o como representación parcial de otros procesos.

• Por ejemplo al compilar un programa en C en Windows o DOS, se produce un código objeto con extensión .obj para que posteriormente el enlazador cree finalmente el código executable .exe

Page 11: Etapas finales de un traductor

Lenguajes Intermedios• En sistemas basados en Unix, también

ocurre algo similar generándose un archivo .o y el executable a.out

• Otros lenguajes intermedios famosos son los generados para la máquina virtual de Java el bytecode; y para la máquina virtual de .NET el MISL para luego ejecutarse en tiempo de ejecución JIT (Just in Time)

Page 12: Etapas finales de un traductor

Lenguajes Intermedios• Otros lenguajes intermedios se utilizan en

sistemas distribuidos como RPC, CORBA y su IDL, etc.

• En este caso estos lenguajes intermedios se encargan de enmascarar toda la heterogeneidad de las comunicaciones distribuidas en una computadora

Page 13: Etapas finales de un traductor

Notaciones• Las notaciones sirven de base para

expresar sentencias bien definidas.

• El uso más extendido de las notaciones sirve para expresar operaciones aritméticas.

• Las expresiones aritméticas se pueden expresar de tres formas distintas: infija, prefija y postfija.

Page 14: Etapas finales de un traductor

Notaciones• La diversidad de notaciones corresponde

en que para algunos casos es más sencillo un tipo de notación.

• Las notaciones también dependen de cómo se recorrerá el árbol sintáctico, el cual puede ser en inorden, preorden o postorden; teniendo una relación de uno a uno con la notación de los operadores.

Page 15: Etapas finales de un traductor

Infija• La notación infija es la más utilizada por

los humanos por que es la más comprensible ya que ponen el operador entre los dos operandos. Por ejemplo a+b-5.

• No existe una estructura simple para representar este tipo de notación en la computadora por esta razón se utilizan otras notaciones.

Page 16: Etapas finales de un traductor

Postfija• La notación postfija pone el operador al

final de los dos operandos, por lo que la expresión queda: ab+5-

• La notación posftfija utiliza una estructura del tipo LIFO (Last In First Out) pila, la cual es la más utilizada para la implementación.

Page 17: Etapas finales de un traductor

Prefija• La notación prefija pone el operador

primero que los dos operandos, por lo que la expresión anterior queda: +ab-5.

• Esto se representa con una estructura del tipo FIFO (First In First Out) o cola.

• Las estructuras FIFO son ampliamente utilizadas pero tienen problemas con el anidamiento aritmético.

Page 18: Etapas finales de un traductor

Representación Cod Int.• Existen maneras formales para

representar código intermedio.

• Estas notaciones simplifican la traducción de nuestro código fuente a nuestro código objeto ya que ahorran y acotan símbolos de la tabla de símbolos

Page 19: Etapas finales de un traductor

Código P• El código P hace referencia a máquinas

que utilizan o se auxilian de pilas para generar código objeto.

• En muchos caso la P se asociado a código portable el cual garantiza que el código compilado en una máquina se pueda ejecutar en otras.

Page 20: Etapas finales de un traductor

Código P• Para garantizar la portabilidad del código

se necesita que el lenguaje este estandarizado por algún instituto y que dicho código no tenga extensiones particulares.

• También se recomienda la no utilización de características especiales exclusivas de alguna arquitectura de computadoras en particular.

Page 21: Etapas finales de un traductor

Triplos• Las proposiciones de tres direcciones se

parece mucho al ensamblador, el cual es un lenguaje intermedio más entendible para la máquina.

• Las estructuras de control (if, switch, while, do-while, for) son realmente etiquetas goto disfrazadas.

Page 22: Etapas finales de un traductor

Triplos• El problema de utilizar cuádruplos radica

en que se tienen que colocar los valores temporales en la tabla de símbolo.

• Con una estructura de tres campos se pueden omitir los valores temporales, dicha estructura recibe el nombre de triples y tiene los siguientes campos: op, arg1 y arg2

Page 23: Etapas finales de un traductor

Triplos• Generalmente el código que generan los

triples recibe el nombre de código de dos direcciones, aunque en ocasiones puede variar.

• Cuando se utilizan triples se ocupan punteros a la misma estructura de los triples.

• b t1 t2 //cuádruplos • • b (0) //triple

Page 24: Etapas finales de un traductor

Triplos• Se debe tener en cuenta el proceso de

asignación, de declaración, expresiones booleanas.

• Las expresiones lógicas también pueden pasarse a código de tres direcciones, utilizando para ello expresiones en corto circuito.

Page 25: Etapas finales de un traductor

Triplos• La evaluación de expresiones en corto

circuito implica que se evalúan condiciones revisando valores anteriores; por ejemplo, para el operador AND con una condición que se detecte como falsa toda la expresión es falsa, en el caso del operador OR si se encuentra una condición verdadera todo será verdadera

• ¿Cómo resuelven los compiladores las expresiones? Forma Normal disyuntiva

Page 26: Etapas finales de un traductor

Triplos• La notación de tres direcciones es una

forma abstracta de código intermedio.

• Esta notación se puede implementar como registros con campos para el operador y operadores.

Page 27: Etapas finales de un traductor

Intérpretes• Los interpretes generalmente utilizan

este triplos para generar el código intermedio para ejecutarse una vez considerado la instrucción como válido.

• En este sentido, un compilador es más difícil de implementar ya que tendrá que mantener todas las estructuras generadas que en muchas ocasiones serán cuadruplos.

Page 28: Etapas finales de un traductor

Cuadruplos• Es una estructura tipo registro con

cuatros campos que se llaman: op, arg1, arg2 y resultado. OP tiene un código intermedio.

• Los operadores unarios como x:=-y no utilizan arg2. Generalmente arg1, arg2 y resultado son valores de tipo puntero y apuntan a una entrada en la tabla de símbolos.

Page 29: Etapas finales de un traductor

Esquemas de Generación• Los esquemas de generación son las

estrategias o acciones que se deberán realizarse y tomarse en cuenta en el momento de generar código intermedio.

• Los esquemas de generación dependen de cada lenguaje. Tomaremos algunos esquemas de generación del lenguaje C.

Page 30: Etapas finales de un traductor

Expresiones• Para generar expresiones estas deben

representarse de manera más simple y más literal para que su conversión sea más rápida.

• Por ejemplo la traducción de operaciones aritméticas debe especificarse una por una, de tal forma que una expresión sea lo más mínimo posible.

Page 31: Etapas finales de un traductor

Declaración de variables• Las declaraciones de variables y

constantes deben separarse de tal manera que queden las expresiones una por una de manera simple.

• Por ejemplo int a,b,c; se descompone a int a; int b; intc; respectivamente.

Page 32: Etapas finales de un traductor

Estatutos de Asignación• Las operaciones de asignación deben

quedar expresadas por una expresión sencilla, si está es compleja se debe reducir hasta quedar un operador sencillo.

• Por ejemplo: x = a+b/5; debe quedar de la forma y = b/5; z = a+y; x=z.

Page 33: Etapas finales de un traductor

Estatuto Condicional• Las condiciones deben expresarse de

manera lo más sencilla posible de tal forma que puedan evaluarse en cortocircuito. Por ejemplo una instrucción como: if (a == b && f!=5&& f%3==0) se evalúa primero x = (a==b && f!=5)y = x && f%3==0; if (y)

• Las instrucciones de decisión compleja como switch se reducen a una versión complejas de if’s

Page 34: Etapas finales de un traductor

Estatuto de Ciclos• Los ciclos se descomponen en un ciclo

genérico, por lo que ciclos while, for y do- while tienen la misma representación interna. En el caso de C, todo queda en forma de while.

• Las condiciones lógicas también pueden ser evaluadas en cortocircuito y reducidas.

Page 35: Etapas finales de un traductor

Arreglos• Los arreglos se descomponen en

estructuras básicas de manejo de manera simple, así por ejemplo: char *a=“Hola”; se reduce a: a[0]=‘H’; a[1]=‘o’; a[2]=‘l’; a[3]=‘a’; a[4]=‘\0’;

Page 36: Etapas finales de un traductor

Funciones• Las funciones pueden reducir a en línea,

lo que se hace es expander el código original de la función.

• Las funciones se descomponen simplificando los parámetros de manera individual al igual que el valor de retorno.

Page 37: Etapas finales de un traductor

Optimización

Etapas Finales del Proceso de Traducción

Page 38: Etapas finales de un traductor

Agenda• Tipos de optimización.

– Locales. – Bucles. – Globales. – De mirilla.

• Costos. – Costo de ejecución. – Criterios para mejorar el código.– Herramientas para el análisis del flujo de

datos.

Page 39: Etapas finales de un traductor

Tipos de Optimización• Las optimizaciones pueden realizarse de

diferentes formas. Las optimizaciones se realizan en base al alcance ofrecido por el compilador.

• La optimización va a depender del lenguaje de programación y es directamente proporcional al tiempo de compilación; es decir, entre más optimización mayor tiempo de compilación.

Page 40: Etapas finales de un traductor

Tipos de Optimización• Como el tiempo de optimización es gran

consumidor de tiempo (dado que tiene que recorrer todo el árbol de posibles soluciones para el proceso de optimización) la optimización se deja hasta la fase de prueba final.

• Algunos editores ofrecen una versión de depuración y otra de entrega o final.

Page 41: Etapas finales de un traductor

Tipos de Optimización• La optimización es un proceso que tiene a

minimizar o maximizar alguna variable de rendimiento, generalmente tiempo, espacio, procesador, etc.

• Desafortunamente no existen optimizador que hagan un programa más rápido y que ocupe menor espacio.

Page 42: Etapas finales de un traductor

Tipos de optimización• La optimización se realiza

reestructurando el código de tal forma que el nuevo código generado tenga mayores beneficios.

• La mayoría de los compiladores tienen una optimización baja, se necesita de compiladores especiales para realmente optimizar el código.

Page 43: Etapas finales de un traductor

Optimización Local• La optimización local se realiza sobre

módulos del programa. En la mayoría de las ocasiones a través de funciones, métodos, procedimientos, clases, etc.

• La característica de las optimizaciones locales es que sólo se ven reflejados en dichas secciones.

Page 44: Etapas finales de un traductor

Optimización Local• La optimización local sirve cuando un

bloque de programa o sección es crítico por ejemplo: la E/S, la concurrencia, la rapidez y confiabilidad de un conjunto de instrucciones.

• Como el espacio de soluciones es más pequeño la optimización local es más rápida

Page 45: Etapas finales de un traductor

Optimización de Ciclos• Los ciclos son una de las partes más

esenciales en el rendimiento de un programa dado que realizan acciones repetitivas, y si dichas acciones están mal realizadas, el problema se hace N veces más grandes.

• La mayoría de las optimizaciones sobre ciclos tratan de encontrar elementos que no deben repetirse en un ciclo.

Page 46: Etapas finales de un traductor

Optimización de Ciclos• Sea el ejemplo:

while(a == b) { int c = a; c = 5; …; }

• En este caso es mejor pasar el int c =a; fuera del ciclo de ser posible.

Page 47: Etapas finales de un traductor

Optimización de ciclos• El problema de la optimización en ciclos y

en general radica es que muy difícil saber el uso exacto de algunas instrucciones. Así que no todo código de proceso puede ser optimizado.

• Otros uso de la optimización pueden ser el mejoramiento de consultas en SQL o en aplicaciones remotas (sockets, E/S, etc.)

Page 48: Etapas finales de un traductor

Optimización Global• La optimización global se da con respecto

a todo el código.

• Este tipo de optimización es más lenta pero mejora el desempeño general de todo programa.

• Las optimizaciones globales pueden depender de la arquitectura de la máquina.

Page 49: Etapas finales de un traductor

Optimización Global• En algunos casos es mejor mantener

variables globales para agilizar los procesos (el proceso de declarar variables y eliminarlas toma su tiempo) pero consume más memoria.

• Algunas optimizaciones incluyen utilizar como variables registros del CPU, utilizar instrucciones en ensamblador.

Page 50: Etapas finales de un traductor

Optimización de Mirilla• La optimización de mirilla trata de

estructurar de manera eficiente el flujo del programa, sobre todo en instrucciones de bifurcación como son las decisiones, ciclos y saltos de rutinas.

• La idea es tener los saltos lo más cerca de las llamadas, siendo el salto lo más pequeño posible

Page 51: Etapas finales de un traductor

Costos• Los costos son el factor más importante a

tomar en cuenta a la hora de optimizar ya que en ocasiones la mejora obtenida puede verse no reflejada en el programa final pero si ser perjudicial para el equipo de desarrollo.

• La optimización de una pequeña mejora tal vez tenga una pequeña ganancia en tiempo o en espacio pero sale muy costosa en tiempo en generarla.

Page 52: Etapas finales de un traductor

Costos• Pero en cambio si esa optimización se

hace por ejemplo en un ciclo, la mejora obtenida puede ser N veces mayor por lo cual el costo se minimiza y es benéfico la mejora.

• Por ejemplo: for(int i=0; i < 10000; i++); si la ganancia es de 30 ms 300s

Page 53: Etapas finales de un traductor

Costos de Ejecución• Los costos de ejecución son aquellos que

vienen implícitos al ejecutar el programa.

• En algunos programas se tiene un mínimo para ejecutar el programa, por lo que el espacio y la velocidad del microprocesadores son elementos que se deben optimizar para tener un mercado potencial más amplio.

Page 54: Etapas finales de un traductor

Costos de Ejecución• Las aplicaciones multimedia como los

videojuegos tienen un costo de ejecución alto por lo cual la optimización de su desempeño es crítico, la gran mayoría de las veces requieren de procesadores rápidos (e.g. tarjetas de video) o de mucha memoria.

• Otro tipo de aplicaciones que deben optimizarse son las aplicaciones para dispositivos móviles.

Page 55: Etapas finales de un traductor

Costos de Ejecución• Los dispositivos móviles tiene recursos

más limitados que un dispositivo de cómputo convencional razón por la cual, el mejor uso de memoria y otros recursos de hardware tiene mayor rendimiento.

• En algunos casos es preferible tener la lógica del negocio más fuerte en otros dispositivos y hacer uso de arquitecturas descentralizadas como cliente/servidor o P2P.

Page 56: Etapas finales de un traductor

Criterios Mejora de Software• La mejor manera de optimizar el código

es hacer ver a los programadores que optimicen su código desde el inicio, el problema radica en que el costo podría ser muy grande ya que tendría que codificar más y/o hacer su código mas legible.

• Los criterios de optimización siempre están definidos por el compilador

Page 57: Etapas finales de un traductor

Criterios de Optimización• Muchos de estos criterios pueden

modificarse con directivas del compilador desde el código o de manera externa.

• Este proceso lo realizan algunas herramientas del sistema como los ofuscadores para código móvil y código para dispositivos móviles.

Page 58: Etapas finales de un traductor

Htas. Análisis Flujo Datos• Existen algunas herramientas que

permiten el análisis de los flujos de datos, entre ellas tenemos los depuradores y desambladores.

• La optimización al igual que la programación es un arte y no se ha podido sistematizar del todo.

Page 59: Etapas finales de un traductor

Generación de Código Objeto

Juan Carlos Olivares Rojas

Page 60: Etapas finales de un traductor

Agenda• Lenguaje máquina.

– Características. – Direccionamiento.

• Lenguaje ensamblador. – Características. – Almacenamiento.

• Registros. – Distribución. – Asignación.

• Administración de memoria.

Page 61: Etapas finales de un traductor

Lenguaje Máquina• El lenguaje máquina sólo es entendible

por las computadoras. Se basa en una lógica binaria de 0 y 1, generalmente implementada por mecanismos eléctricos.

• En general el lenguaje máquina es difícil de entender para los humanos por este motivo hacemos uso de lenguajes más parecidos a los lenguajes naturales.

Page 62: Etapas finales de un traductor

Características• El lenguaje máquina realiza un conjunto

de operaciones predeterminadas llamadas microoperaciones.

• Las microoperaciones sólo realizan operaciones del tipo aritmética (+,-,*, /), lógicas (AND, OR, NOT) y de control (secuencial, decisión, repetitiva)

Page 63: Etapas finales de un traductor

Características• El lenguaje máquina es dependiente del

tipo de arquitectura. Así un programa máquina para una arquitectura intel x86 no se ejecutará en una arquitectura Power PC de IBM (al menos de manera nativa).

• Algunos microprocesadores implementan más funcionalidades llamado CISC, pero son más lentos que los RISC ya que estos tienen registros más grandes.

Page 64: Etapas finales de un traductor

Direccionamiento• Es la forma en como se accede a la

memoria. Recordar que un programa no puede ejecutarse sino se encuentra en memoria principal.

• La forma de acceder a la memoria depende del microprocesador, pero en general existen dos tipos de direccionamiento: directo e indirecto.

Page 65: Etapas finales de un traductor

Direccionamiento• El direccionamiento directo también

recibe el nombre de direccionamiento absoluto y el acceso a las direcciones se hace de manera directa.

• El direccionamiento indirecto también recibe el nombre de direccionamiento relativo y se basa a partir de una dirección genérica, generalmente el inicio del programa.

Page 66: Etapas finales de un traductor

Direccionamiento• Para acceder a una dirección relativa se

suma a la dirección base el número de espacios de memorias necesarias.

• El direccionamiento relativo hace a los programas relocalizables e independientes.

• Si la dirección base es el inicio de la memoria fija el direccionamiento pasa a ser un variante de direccionamiento absoluto.

Page 67: Etapas finales de un traductor

Lenguaje Ensamblador• El ensamblador (del inglés assembler) es

un traductor de un código de bajo nivel a un código, ejecutable directamente por la máquina para la que se ha generado.

• Fue la primera abstracción de un lenguaje de programación, posteriormente aparecieron los compiladores.

Page 68: Etapas finales de un traductor

Características• El programa lee un archivo escrito en

lenguaje ensamblador y sustituye cada uno de los códigos mnemotécnicos por su equivalente código máquina.

• Los programas se hacen fácilmente portables de máquina a máquina y el cálculo de bifurcaciones se hace de manera fácil.

Page 69: Etapas finales de un traductor

Ensambladores• Ensambladores básicos. Son de muy bajo

nivel, y su tarea consiste básicamente en ofrecer nombres simbólicos a las distintas instrucciones, parámetros y cosas tales como los modos de direccionamiento.

Page 70: Etapas finales de un traductor

Ensambladores• Ensambladores modulares, o macro

ensambladores. Descendientes de los ensambladores básicos, fueron muy populares en las décadas de los 50 y los 60, antes de la generalización de los lenguajes de alto nivel. Una macroinstrucción es el equivalente a una función en un lenguaje de alto nivel.

Page 71: Etapas finales de un traductor

Almacenamiento• Una de las principales ventajas del uso

del ensamblador, es que se encarga de administrar de manera transparente para el usuario la creación de memoria, las bifurcaciones y el paso de parámetros. • Además nos permite acceder directamente a los recursos de la máquina para un mejor desempeño.

Page 72: Etapas finales de un traductor

Registros• Los registros son la memoria principal de

la computadora. Existen diversos registros de propósito general y otros de uso exclusivo.

• Algunos registros de propósito general son utilizados para cierto tipo de funciones. • Existen registros acumuladores, puntero de instrucción, de pila, etc.

Page 73: Etapas finales de un traductor

Distribución• La distribución es el proceso en el que el

programa generado puede ejecutarse en otras máquinas.

• Con respecto al ensamblador, la mayoría del direccionamiento se hace relativo para que el programa sea relocalizable por un programa llamado cargador

Page 74: Etapas finales de un traductor

Distribución• En el caso de programas compilados se

necesitan de las librerías, si son estáticas se incluyen en el ejecutable por lo que el programa se hace gráfico, si son dinámicas no pero el programa es más pequeño.

• Debido a la complejidad del software actual se necesitan de asistentes para poder instalar y ejecutar un programa

Page 75: Etapas finales de un traductor

Asignación• La asignación de valores a variables se

hace a través de un proceso de mover el contenido de memoria a registro, o de registro a memoria, pero nunca de memoria a memoria.

• Cuando se trata de memoria dinámica se debe seguir el rastro de los datos

Page 76: Etapas finales de un traductor

Administración memoria• La administración de la memoria e sun

proceso hoy en día muy importante, de tal modo que su mal o buen uso tiene una acción directa sobre el desempeño de memoria.

• En general un ensamblador tiene un administrador de memoria más limitado que un compilador.

Page 77: Etapas finales de un traductor

Administración de Memoria• En la mayoría de los lenguajes de

programación el uso de punteros no estaba vigilado por lo que se tienen muchos problemas con el uso de memoria. • Los lenguajes más recientes controlan el uso de punteros y tienen un programa denominado recolector de basura que se encarga de limpiar la memoria no utilizada mejorando el desempeño.

Page 78: Etapas finales de un traductor

Referencias• Aho (2006), et. al. Compiladores:

Principios y Técnicas. Segunda Edición.

Page 79: Etapas finales de un traductor

¿Preguntas?