Repository navigation
Invoke runtime System expression-tree values - #659
Open
jogibear9988 wants to merge 1 commit into
Open
jogibear9988 wants to merge 1 commit into
jogibear9988 wants to merge 1 commit into
Conversation
Invoke handles delegate receivers and literal lambdas, but fails for runtime System.Linq.Expressions.Expression<TDelegate> values. Resolve the typed Compile/Invoke signature, preserve receiver evaluation exactly once, and defer runtime compilation until after arguments when their stack spilling requires it. Teach LightExpression invocation construction to obtain the same return type. Validation: Release solution build and full Standard/LightExpression runners on .NET 8, .NET 10 and .NET Framework. Computed and parameter receivers, changing runtime trees, null and invalid trees, argument/finalizer ordering, incoming ref expression receivers loaded as values, and strict rejection of unsupported by-ref argument signatures.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Invoke handles delegate receivers and literal lambdas, but fails for runtime System.Linq.Expressions.Expression values.
Resolve the typed Compile/Invoke signature, preserve receiver evaluation exactly once, and defer runtime compilation until after arguments when their stack spilling requires it. Teach LightExpression invocation construction to obtain the same return type.
Computed and parameter receivers, changing runtime trees, null and invalid trees, argument/finalizer ordering, incoming ref expression receivers loaded as values, and strict rejection of unsupported by-ref argument signatures.
Calling the runtime expression value’s System Compile method is part of Invoke semantics, not a fallback for compiling the outer FEC lambda. By-ref argument signatures remain unsupported on this path.
Validation: Release solution build; full Standard and LightExpression runners on .NET 8, .NET 10 and .NET Framework. net8.0: 567 TestX cases and 1744 legacy cases; net10.0: 567 TestX cases and 1745 legacy cases; net472: 548 TestX cases and 1610 legacy cases.
Shared-workload measurements
Base:
bac81d0734c0(master); patch:21e24ce0e832. Windows ARM64, SDK 10.0.301; .NET 8.0.28 and 10.0.9. Expression trees and invocation adapters are prepared outside the timed loops. Strict FEC compilation, tiered compilation disabled, one pinned logical processor, two opposite-load-order processes per runtime, seven alternating paired samples per process, 30 ms calibration target; medians of 14 samples.Both columns below are FEC. “System trees” names the expression API, not the System compiler. Compilation includes delegate creation; invocation measures the returned delegate through the same adapter on each side. Managed allocations use GC.GetAllocatedBytesForCurrentThread.
constructor_argumentsdelegate_invokedelegate_two_argumentsscalar_addconstructor_argumentsdelegate_invokedelegate_two_argumentsscalar_addconstructor_argumentsdelegate_invokedelegate_two_argumentsscalar_addconstructor_argumentsdelegate_invokedelegate_two_argumentsscalar_addEmitted IL matched byte-for-byte for 16/16 shared control delegates. Observed compilation changes range from -33.0% to +117.9%; invocation changes from -46.0% to +153.4%. Slower results are retained. Even identical-IL controls vary, so these short machine timings do not establish a blanket runtime speedup or absence of regressions.
Managed allocations were unchanged on every shared workload in this run.
LightExpression tree construction
Invocation nodes are also measured without compiling them. The existing delegate Invoke lookup is attempted first, so ordinary delegate construction does not perform an extra expression-type/Compile lookup. Literal-lambda construction is an unchanged control. 150 ms target, 14 samples.
build_delegate_invocationbuild_literal_invocationbuild_delegate_invocationbuild_literal_invocationRepaired behavior, patch-only measurements
These are executable repaired-case workloads, measured separately from the shared controls. A failed, rejected or incorrect master delegate is not treated as a valid timing baseline. Two isolated loads of the patch provide 14 samples per runtime/API/phase.
fixed_casefixed_case_ignoredfixed_case_voidfixed_casefixed_case_ignoredfixed_case_voidfixed_casefixed_case_ignoredfixed_case_voidfixed_casefixed_case_ignoredfixed_case_void