Lowering takes the SemIR and produces LLVM IR. At present, this is done in a single pass, although it's possible we may need to do a second pass so that we can first generate type information for function arguments.
Lowering is done per SemIR::InstBlock. This minimizes changes to the
IRBuilder insertion point, something that is both expensive and potentially
fragile.
Part of lowering is choosing deterministically unique identifiers for each lowered entity to use in platform object files. Any feature of an entity (such as parent namespaces or overloaded function parameters) that would create a distinct entity must be included in some way in the generated identifier.
The current rudimentary name mangling scheme is as follows:
Main.Run is emitted as main.Otherwise the resulting name consists of:
_C.impl, then add:
:The scope mangling scheme is as follows:
..package P1;
interface Interface {
fn Op[self: Self]();
}
namespace NameSpace;
class NameSpace.Implementation {
// Mangled as:
// `_COp.Implementation.NameSpace.Main:Interface.P1`
impl as P1.Interface {
fn Op[self: Self]() {
}
}
}
// Mangled as `main`.
fn Run() {
var v: NameSpace.Implementation;
v.(P1.Interface.Op)();
}