Reggie, the experimental Gleam -> WASM compiler (mirror) reggie.desertthunder.dev
regulus docs book src chapter_3.md
1.6 kB · 47 lines
Markdown
at main

Name resolution #

Names are how a program connects pieces of code. In Gleam, a name might refer to a function, a parameter, a local variable, a type, a constructor, a record field, or an imported module:

import gleam/io

fn greet(name) {
  let message = "Hello, " <> name
  io.println(message)
}

This program has several names: io, greet, name, message, and println. The source text only tells us how those names are spelled. Name resolution works out what each name refers to.

A common compiler definition is that name resolution connects references to the declarations they denote.[1] That sounds small, but it is one of the places where a language's rules become concrete. The compiler has to decide which names are visible, what happens when two names are the same, and whether a name like io.println means a module function or a field access.

For this project, the path is:

Gleam AST
  -> scopes and symbols
  -> resolved references

The parser keeps names as text. The resolver turns those names into stable symbol IDs and qualified member references that later compiler passes can use.

This chapter covers name resolution in more detail, including:

  • lexical scope and shadowing
  • bindings, references, scopes, and symbol tables
  • namespaces, imports, and qualified names
  • pattern bindings, visibility, and package graphs
  • the resolver implemented in this compiler

  1. Pierre Neron, Andrew Tolmach, Eelco Visser, and Guido Wachsmuth, "A Theory of Name Resolution": https://researchr.org/publication/NeronTVW15 ↩︎