The `serialize` method can be called multiple times, but it will perform the actual serialization only the first time.
By means of this API we get the flexibility to serialize the SILModule not only after all the optimizations, but e.g. at any time during optimizations.
The reason that I am doing this is in preparation for adding support for
MultipleValueInstruction. This enables us to avoid type issues and also ensures
that we do not increase the size of SingleValueInstruction while we are doing
it.
The MultipleValueInstruction commit will come soon.
rdar://31521023
Except GenericEnvironment.h, because you can't meaningfully use a
GenericEnvironment without its signature. Lots less depends on
GenericSignature.h now. NFC
This will allow us to remove dynamic_method, emitting objc_method
in its place. It will also allow objc_method to be used for
Objective-C protocol method calls, with witness_method used
for Swift native protocol method calls only.
This replaces the '[volatile]' flag. Now, class_method and
super_method are only used for vtable dispatch.
The witness_method instruction is still overloaded for use
with both ObjC protocol requirements and Swift protocol
requirements; the next step is to make it only mean the
latter, also using objc_method for ObjC protocol calls.
Update the SILBuilder and other relevant bits of SILGen s.t we pass
along branch taken counts whenever we create conditional branches.
There is a lot of unfinished work here: we need to teach ParseSIL,
DeserializeSIL, and the SILOptimizer about profile data. And add a
stable AST hasher. And add tests for it all.
Let's skip all of that for now. Next, we'll wire in some actual profile
data.
introduce a common superclass, SILNode.
This is in preparation for allowing instructions to have multiple
results. It is also a somewhat more elegant representation for
instructions that have zero results. Instructions that are known
to have exactly one result inherit from a class, SingleValueInstruction,
that subclasses both ValueBase and SILInstruction. Some care must be
taken when working with SILNode pointers and testing for equality;
please see the comment on SILNode for more information.
A number of SIL passes needed to be updated in order to handle this
new distinction between SIL values and SIL instructions.
Note that the SIL parser is now stricter about not trying to assign
a result value from an instruction (like 'return' or 'strong_retain')
that does not produce any.
The declarations that I moved into the header on master do not
match the versions for master-next. This just updates the header
to match the template instantiations in lib/SIL/Dominance.cpp.
These will be used for unit-testing the Type::join functionality in the
type checker. The result of the join is replaced during constraint
generation with the actual type.
There is currently no checking for whether the arguments can be used to
statically compute the value, so bad things will likely happen if
e.g. they are type variables. Once more of the basic functionality of
Type::join is working I'll make this a bit more bullet-proof in that
regard.
They include:
// Compute the join of T and U and return the metatype of that type.
Builtin.type_join<T, U, V>(_: T.Type, _: U.Type) -> V.Type
// Compute the join of &T and U and return the metatype of that type.
Builtin.type_join_inout<T, U, V>(_: inout T, _: U.Type) -> V.Type
// Compute the join of T.Type and U.Type and return that type.
Builtin.type_join_meta<T, U, V>(_: T.Type, _: U.Type) -> V.Type
I've added a couple simple tests to start off, based on what currently
works (aka doesn't cause an assert, crash, etc.).
The main part of the change is to support the ptr_to_int builtin in statically initialized globals. This builtin is used to build a StaticString from a string_literal.
On the other hand I removed the support of the FPTrunc builtin, which is not needed anyway (because it can be constant propagated).