Open JosephTremoulet opened 8 years ago
Correction: the arguments to the interface call don't all need to be invariant, just the instance pointer (or more precisely its exact run-time type).
When I originally posted this issue to Connect I was thinking that it could help with enumerators and small loops, where the relative cost of calling MoveNext
/Current
through an interface is significant. See dotnet/coreclr#8481 for an example that doesn't involve enumerators and has more complex code. The issue is about sort calling a delegate via an interface method but then it turned out that doing exactly the opposite is good either way because interface calls are slower than delegate calls.
When all of the arguments of an interface call are invariant w.r.t. a containing loop, the jit could rewrite the interface call as a call to
CORINFO_HELP_VIRTUAL_FUNC_PTR
to fetch the function pointer followed by an indirect call on that pointer; the helper call could then be hoisted from the loop. This would remove a couple levels of indirection (i.e. dereferencing the cell, jumping to the thunk, verifying in the thunk that the callsite is monomorphic, and dereferencing the cached function pointer) per loop iteration. I presume that this would have to be weighed against the cost of redoing the lookup on each invocation of the method being compiled, which (if I understand our thunk calls correctly) would otherwise have its result cached across invocations.[I'm migrating an optimization suggestion from Connect to GitHub]
category:cq theme:loop-opt skill-level:expert cost:medium