Fix dotnet/coreclr#6893. (dotnet/coreclr#6932)
Aggregate arguments to calls (i.e. arguments that are made up
of multiple, independent values such as those to be passed in
multiple registers) are represented by GT_LIST nodes that are
not distiguishable from normal GT_LIST nodes without the extra
context of the call. GT_LIST nodes, however, are disallowed in
LIR ranges. The intersection of these two design choices causes
problems for code that operates on LIR but wants to observe
aggregate arguments as a whole (rather than piecewise). In the
case of dotnet/coreclr#6893, this caused lowering to attempt to insert a
PUTARG_STK node after the GT_LIST node that represented the
aggregate argument that was being forced to the stack, which
caused an assertion in the LIR utilities to fail (the GT_LIST
node was passed as the insertion point to `LIR::Range::InsertAfter`,
which requires that the insertion point be a part of the given
range).
Conceptually, the fix is simple: the nodes that represent
aggregate arguments must be allowed to be part of LIR ranges.
The implementation, however, is complicated somewhat by the
need to distinguish the nodes used for aggregate arguments from
normal GT_LIST nodes. These changes implement a short-term
fix that distiguished these nodes by adding a node-specific flag,
`GTF_LIST_AGGREGATE`, to indicate that a GT_LIST node is in fact
an aggregate argument. In the long term, a more palatable
implementation would be the introduction of a new node and operator
type to represent aggregate arguments, but this is likely to
require broader changes to the compiler.
Commit migrated from https://github.com/dotnet/coreclr/commit/
fd5a96d96fdcc4a1a439b211d15ceca3a110a1eb