AjTalk: Implementando un intérprete tipo Smalltalk (Parte 1) Estructura de objetos

Published on Author lopez2 Comments

Comienzo a escribir sobre las decisiones de diseño que tuve que tomar para armar AjTalk, mi intérprete tipo Smalltalk de código abierto escrito en C#. Hay una largar tradición en el armado de máquinas virtuales Smalltalk. Veamos qué pude armar y por qué.

En est primer post quiero exporar cómo implementar el concepto central de todo compilador o intérprete que soporta objetos tipo Smalltalk. Un objeto en Smalltalk clásico tiene un estado interno, representado por variables de instancia (dejemos por un tiempo las variables indexadas). Una primera vista:

En muchas implementaciones de Smalltalk (incluyendo las primeras, como el clásico Smalltalk-80), cada objeto contiene valores de un tipo: cada objeto contiene ya sea, bytes, o words o punteros a otros objetos:

Es usal que algunos valores, antes It is also usual that some values, enlugar de ser punteros, son valores “primitivos” como los valores enteros. Para diferenciar un puntero de otro objeto, como un valor entero, algunos bits de la palabra que almacena el puntero/entero son usados para distinguir los dos casos. Un puntero puede referenciar a otro objeto:

Otras implementaciones usan un tabla de objetos. Los punteros referencian celdas de esa tabla, en vez de referenciar directamente al objeto:

Una tabla de objetos puede tener, en cada celda, información sobre el objeto, como su tipo, su clase, y el lugar en memoria de su estado interno. La estrategia de tabla de objetos simplifica operaciones como el “become:” y el “garbage collection” (la “recolección de basura”, detección y liberación de la memoria ya no usada). Puede ser usada para remover un mensaje de memoria y recuperarlo cuando un mensaje le sea enviado. Entonces, la celda tendría la información de persistencia.

¿Cómo implementar estas características en AjTalk? Desde el comienzo quise que AjTalk pueda acceder y manejar objetos .NET nativos. Así que permito dos tipos de objetos: los objetos .NET nativos (enteros, strings, arreglos, objetos de la librería de clases, por ejemplo, ADO.NET, etc..), y los objetos AjTalk. Así que en vez de manejar objetos que sólo contengan bytes, words o punteros, decidí que los objetos AjTalk tengan variables instancias que referencian a cualquier objeto, sea .NET o AjTalk.

Internamente, un objeto AjTalk mantiene un arreglo de objetos:

[Serializable]
public class BaseObject : IObject, ISerializable
{
    private IBehavior behavior;
    private object[] variables; // pointers to objects
    // ...
}


Un elemento de ese arreglo puede referenciar a un entero, un caracter, es decir, objetos primitivos, u objetos más complejos. .NET permite apuntar a valores elementales usando “boxing”, colocando esos valores dentro de un objeto en la memoria dinámica. Es el precio a pagar para tener la flexibilidad de manejar todo tipo de objetos: usar boxing/unboxing. Afortunadamente, .NET maneja ese mecanismo de forma transparente. Desde el punto de vista de código C#, todo ese almacenamiento via “boxing” no necesita ser explícito. Esta forma de armar objetos AjTalk también delega el manejo de “garbage collection” a la propia implementación de .NET.

Próximos pasos: explorar cómo implementar mensajes y su invocación, clases y herencia, y más.

Nos leemos!

Angel “Java” Lopez

http://www.ajlopez.com

http://twitter.com/ajlopez

Leave a Reply

Your email address will not be published. Required fields are marked *