Back to flin
flin

El opcode duplicado que casi rompió todo

Cómo un handler duplicado del opcode CreateMap en la VM de FLIN descartaba silenciosamente claves de mapas -- descubierto durante la auditoría, corregido en una línea de Rust.

Juste Thales Gnimavo & Claude | March 26, 2026 2 min flin
EN/ FR/ ES
flinrust

Los peores errores no son los que hacen que su programa se caiga. Los peores errores son los que silenciosamente producen resultados incorrectos. FLIN tenía tal error. Dos implementaciones separadas del mismo opcode, viviendo en el mismo archivo, separadas por 3,418 líneas, produciendo resultados sutilmente diferentes dependiendo de qué ruta de ejecución tomara la VM.

El opcode CreateMap -- responsable de construir cada hash map en cada programa FLIN -- existía en dos formas. Una manejaba claves Value::Text. La otra no. Y durante semanas, los mapas de traducción estaban silenciosamente descartando entradas.

La corrección

La corrección fue quirúrgica -- una rama else if agregada a la versión run() de CreateMap:

rust} else if let Value::Text(s) = key {
    map.insert(s, value);  // <-- LA CORRECCIÓN: manejar Value::Text
}

Una línea de Rust. Tres tokens: else if let. Esa fue la diferencia entre mapas de traducción que funcionaban y mapas de traducción que silenciosamente descartaban entradas.

Lecciones para implementadores de lenguajes

  1. Nunca duplicar tablas de despacho. Si dos funciones necesitan manejar el mismo conjunto de opcodes, deben compartir un único mecanismo de despacho.
  2. El fallthrough silencioso siempre está mal para despacho de opcodes. Un _ => continue silencioso era la causa raíz de docenas de fallos silenciosos.
  3. La elección de representación de valores del compilador nunca debe afectar la semántica.

Esta es la Parte 147 de la serie "Cómo construimos FLIN", que documenta cómo un CEO en Abidjan y un CTO de IA diseñaron y construyeron un lenguaje de programación desde cero.

Navegación de la serie: - [146] Auditando 186,000 líneas de código - [147] El opcode duplicado que casi rompió todo (estás aquí) - [148] 30 TODOs, 5 panics en producción, 0 problemas de seguridad

Share this article:

Responses

Write a response
0/2000
Loading responses...

Related Articles

Thales & Claude deblo

El prompt decía que lo anunciara. El modelo no lo hizo. Así que lo hizo el worker: cerrar un silencio de 15 segundos en Déblo Voice

Déblo Voice se quedaba en silencio unos 15 segundos cada vez que una pregunta difícil activaba una búsqueda profunda. El prompt ya exigía un anuncio, pero el modelo de audio nativo emite la llamada a la función como su primer token. Además, el silencio tenía dos partes, la ejecución de la herramienta y la latencia de la respuesta, así que ningún prompt podía cerrarlo. Llevamos la garantía al worker de LiveKit: un anuncio pregrabado con la voz y el idioma de la sesión, y un suave sonido de tecleo mientras el agente piensa. Probado en producción el 16 de octubre de 2026: 14 y 17,5 segundos de silencio del lado del modelo, unos 0,4 segundos percibidos por el usuario.

13 min Oct 16, 2026
deblodeblo-voicevoice-aigemini-live +17
Thales & Claude zerosuite

El servidor que no dimos de baja: vaciar una máquina de producción en una noche, y cada número que comprobamos

Una noche, seis aplicaciones migradas fila por fila, tres copias de seguridad vacías, una sin destino y un servidor cuyo futuro cambió tres veces.

19 min Oct 2, 2026
caspclaude-codeclaude-opus-5.5infrastructure +10
Thales & Claude zerosuite

El orquestador no programa: trece sesiones en un día, un navegador que verifica y saber cuándo parar

Un día, una plataforma privada de un cliente, trece sesiones headless de Claude encadenadas por un orquestador que nunca escribe código. Verificar en el navegador del CEO, agrupar correcciones sin soltar la gate y escribir cuándo cerrar una sesión.

19 min Sep 30, 2026
caspclaude-codeclaude-opus-5.5multi-session +12