Description
From status quo the proposed change is very small:
- Keyword is renamed from
usingnamespace
toincludenamespace
. - It only mixes in to the set of declarations for a given namespace; it does not affect identifiers.
Example:
pub const Foo = struct {
includenamespace Bar;
test {
_ = hello; // error: use of undeclared identifier
_ = Foo.hello; // OK!
}
};
pub const Bar = struct {
pub const hello = "hello";
}
Why? What material benefit does this have? Turns out, it's actually a big deal for the design of an incremental compiler:
-
AstGen is the place where we report shadowing of identifiers and unused identifiers. It would make sense to also report error for use of undeclared identifier. However the existence of
usingnamespace
makes that not an option. Having this error in AstGen means that the compile error is available non-lazily. That is, you will see errors of this form even for code that does not get semantically analyzed. For example, on Windows you would still see "use of undeclared identifier" errors when building for macOS. -
With status quo semantics, an identifier in scope of more than one
usingnamespace
forces all of them to be resolved, in order to make sure there are no name conflicts. However, usinga.b
syntax means only theincludenamespace
declarations that apply toa
must be resolved. With incremental compilation, having an identifier force an unrelatedusingnamespace
to be resolved creates a dependency between these two things. This dependency costs perf, memory, and decreases the amount of encapsulation of changes - that is, it makes an incremental update less incremental. Theincludenamespace
semantics reduce the amount of such dependencies.