With this commit, the `simplifyTerminator` helper function used by IDS
stops trying to merge the default cases with one of the other cases
arbitrarily.
Now, if the `UnreachableSuccessor` was reached via the default case, the
default case is still arbitrarily redirected to an arbitrary case
successor, but the case and the default do not get merged.
This keeps the logic of the transform simpler, and also allows for
easier successive manipulation by planned upcoming transforms.
The implementation of `simplifyTerminator` is very specific to the
operations of IDS, can be easily misused, and is not currently used
anywhere else in the codebase.
We now reduce the number of cases in which we restart the collection of
the `DivergenceDescriptor`s after a IDS modification on the `ScopeGraph`
is performed.
We previously restarted the collection after each IDS transformation.
Now, restart is only performed after IDS is applied on a `Conditional`
node whose all successors are divergent exits which are `goto` exits.
After such `Conditional` is processed, it may happen that a new `goto`
exit becomes divergent for another `Conditional` upwards in the
`ScopeGraph`.
Therefore, if we do not restart, it may happen that a non-`goto` exit is
processed before a `goto` exit, which may lead to suboptimal situations
in the emitted number of `goto`s, due to how IDS interacts with
`MaterializeTrivialGotos`.
When performing the IDS procedure for a divergence which is entered
through multiple `Successor`s of the `Conditional`, we insert a `Head`
header which collects the entry to the scope, in order to maintain
decidedness if there is a common post-dominator to all the `Successor`s
(similar to what weaving did).
Perform the IDS transformation, by taking into account possible multiple
divergent scopes for a certain conditional node at the same time.
This reduces the run times, since it reduces the number of time IDS is
called on a conditional, but mostly proceduce a more _compact_
`ScopeGraph`, where all the divergent scopes for a certain conditional
node rejoing the path toward the one true exit in a single point,
instead of having a chain of IDS resulting regions.
Make IDS unit tests compliant with the new multiple divergence
implementation.
Perform the IDS operation for the exit nodes corresponding to `goto`
blocks afterwards the other _standard_ exits have been processed.
In addition, order the `GotoBlock`s according to the `post_order` of the
target blocks of the `goto` themselves. This should maximize the
opportunities for later runs of `MaterializeTrivialGoto`.
Introduce the `inline-divergent-scopes` pass. This pass in is charge of
reducing the exit nodes in a `ScopeGraph`, applying the _Inline
Divergent Scopes_ transformation, which is able, in presence of
divergent exits nodes, wrt. to a conditional, to remove the exit node
and to transform the `ScopeGraph` in a form where semantics is
preserved.