This allows reporting successful and unsuccessful optimizations similar to
clang/llvm.
This first patch adds support for the
options -Rpass=<pass-name-regex> -Rpass-missed=<pass-name-regex>. These allow
reporting successful/unsuccessful optimization on the compiler output for passes
specified by the regex. I've also added one missed and one passed remark type
to the inliner to test the infrastructure.
Clang also has the option of collecting these records in an external YAML data
file. This will be added in a later patch.
A few notes:
* The goal is to use this facility for both user-lever "performance" warnings
and expert-level performance analysis. There will probably be a flag in the
future differentiating the verbosity.
* The intent is match clang/llvm as much as it makes sense. On the other hand I
did make some changes. Unlike in llvm, the emitter is not a pass which
simplifies things. Also the remark class hierarchy is greatly simplified since
we don't derive from DiagnosticInfo. We also don't derive from Diagnostic to
support the streaming API for arbitrary named-value pairs.
* Currently function names are printed mangled which should be fixed.
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 reason to do this is:
1. The check in SILInliner if we can inline can be done without triggering
side-effects.
2. This enables us to know if inlining will succeed before attempting to inline.
This enables for arguments to be adjusted with new SILInstructions and the like
before inlining occurs. I use this in a forthcoming patch that updates mandatory
inlining for ownership.
rdar://31521023
If some functions are explicitly annotated by developers as @inline(__always) or @_transparent, they should always be a subject for the inlining of generics, even if this kind of inlining is not enabled currently for all functions.
If some functions are explicitly annotated by developers as @inline(__always) or @_transparent, they should always be a subject for the inlining of generics, even if this kind of inlining is not enabled currently for all functions.
A function is pure if it has no side-effects.
If there is a call of a pure function with constant arguments, it always makes sense to inline it, because we know that the whole computation will be constant folded.
Replace `NameOfType foo = dyn_cast<NameOfType>(bar)` with DRY version `auto foo = dyn_cast<NameOfType>(bar)`.
The DRY auto version is by far the dominant form already used in the repo, so this PR merely brings the exceptional cases (redundant repetition form) in line with the dominant form (auto form).
See the [C++ Core Guidelines](https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#es11-use-auto-to-avoid-redundant-repetition-of-type-names) for a general discussion on why to use `auto` to avoid redundant repetition of type names.
SubstitutionMap::lookupConformance() would map archetypes out
of context to compute a conformance path. Do the same thing
in SubstitutionMap::lookupSubstitution().
The DenseMap of replacement types in a SubstitutionMap now
always has GenericTypeParamTypes as keys.
This simplifies some code and brings us one step closer to
a more efficient representation of SubstitutionMaps.
At some point, pass definitions were heavily macro-ized. Pass
descriptive names were added in two places. This is not only redundant
but a source of confusion. You could waste a lot of time grepping for
the wrong string. I removed all the getName() overrides which, at
around 90 passes, was a fairly significant amount of code bloat.
Any pass that we want to be able to invoke by name from a tool
(sil-opt) or pipeline plan *should* have unique type name, enum value,
commend-line string, and name string. I removed a comment about the
various inliner passes that contradicted that.
Side note: We should be consistent with the policy that a pass is
identified by its type. We have a couple passes, LICM and CSE, which
currently violate that convention.
This is important in case the inline restarts the pass pipeline.
In a sub-sequent invocation of the inlined it should receive a cleaned-up function so that it can make better estimations for further inlining.
As a compensation, reduce the caller-block limit of the inliner.
And add an overall block limit which is also taken into account for always-inline functions.
array.append_element(newElement: Element)
array.append_contentsOf(contentsOf newElements: S)
And allow early inlining of them.
Those functions will be needed to optimize Array.append(contentsOf)
Also, add a third [serializable] state for functions whose bodies we
*can* serialize, but only do so if they're referenced from another
serialized function.
This will be used for bodies synthesized for imported definitions,
such as init(rawValue:), etc, and various thunks, but for now this
change is NFC.
ASTContext::getSpecializedConformance() already copies the
substitutions, so remove some AllocateCopy() calls.
Also, add a new overload taking a SubstitutionMap instead.
This allows removing some gatherAllSubstitutions() calls,
which have an allocation inside them.
Finally, remove the now-unused ModuleDecl parameter from
ProtocolConformance::subst() and make it public.
Partial specialization is disabled by default. Use -sil-partial-specialization to enable it.
Use -sil-partial-specialization-with-generic-substitutions to enable the partial specialization even in cases of substitutions containing generic replacement types.
This reverts commit 1b3d29a163, reversing
changes made to b32424953e.
We're seeing a handful of issues from turning on inlining of generics,
so I'm reverting to unblock the bots.
For a long time, we have:
1. Created methods on SILArgument that only work on either function arguments or
block arguments.
2. Created code paths in the compiler that only allow for "function"
SILArguments or "block" SILArguments.
This commit refactors SILArgument into two subclasses, SILPHIArgument and
SILFunctionArgument, separates the function and block APIs onto the subclasses
(leaving the common APIs on SILArgument). It also goes through and changes all
places in the compiler that conditionalize on one of the forms of SILArgument to
just use the relevant subclass. This is made easier by the relevant APIs not
being on SILArgument anymore. If you take a quick look through you will see that
the API now expresses a lot more of its intention.
The reason why I am performing this refactoring now is that SILFunctionArguments
have a ValueOwnershipKind defined by the given function's signature. On the
other hand, SILBlockArguments have a stored ValueOwnershipKind. Rather than
store ValueOwnershipKind in both instances and in the function case have a dead
variable, I decided to just bite the bullet and fix this.
rdar://29671437
Changes:
* Terminate all namespaces with the correct closing comment.
* Make sure argument names in comments match the corresponding parameter name.
* Remove redundant get() calls on smart pointers.
* Prefer using "override" or "final" instead of "virtual". Remove "virtual" where appropriate.