# The Reachability Requirement

When building a program, the linker determines which units (interfaces and modules) to include by traversing a directed graph. The nodes of the graph correspond to program units, and certain nodes of the graph are designated as roots. A unit u is included in the build if and only if u is reachable from some root, that is, if there exists a (possibly empty) path in the graph from some root r to u. We must now describe how the linker determines the set of roots and the set of edges in this graph.

Each program's m3makefile specifies a set of sources via quake calls like interface(X), implementation(X), and module(X). Each of these calls adds the name of the source file (or unit) to the set of program sources. These program sources constitute the set of roots used to start the traversal. Notice that source files included via include_dir(D) or include_pkg(P) will get added to this list, but not those imported via import(P).

The edges of the graph are determined by the IMPORT and EXPORTS relations among the units. An edge exists in the graph from the unit A to the unit B if and only if:

- A IMPORTs B,
- A EXPORTS B, or
- B EXPORTS A.

That is, if A IMPORTs B, then there is a directed edge from A to B in the graph, but if A EXPORTS B, then there is a bi-directional edge between A and B.