Automatic tail-call optimization (auto-TCO) in StaticOptimizer#694
Draft
He-Pin wants to merge 1 commit intodatabricks:masterfrom
Draft
Automatic tail-call optimization (auto-TCO) in StaticOptimizer#694He-Pin wants to merge 1 commit intodatabricks:masterfrom
He-Pin wants to merge 1 commit intodatabricks:masterfrom
Conversation
7adb221 to
da38f7c
Compare
3532dbf to
2755bea
Compare
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.
Motivation
Jsonnet programs often use recursive functions that are naturally tail-recursive (the recursive call is the last expression in a branch). Without tail-call optimization (TCO), these hit StackOverflowError on deep recursion. Currently, sjsonnet supports TCO via explicit
TailCallnodes, but users must manually structure their code to trigger it.Key Design Decision
Implement automatic TCO detection in the
StaticOptimizer. During the optimization pass, analyze function bodies to identify tail-position calls and automatically rewrite them to useTailCallnodes. This happens transparently — no source code changes needed.Modification
sjsonnet/src/sjsonnet/StaticOptimizer.scala:if/elsebranches,localbindings)Apply*to theTailCallvariantsjsonnet/src/sjsonnet/Expr.scala:Exprnode types for automatic tail callssjsonnet/src/sjsonnet/ExprTransform.scala:sjsonnet/src/sjsonnet/Evaluator.scala:sjsonnet/src/sjsonnet/Val.scala:Tests:
new_test_suite/auto_tco.jsonnet— verifies deep recursion (>10000 depth) works with auto-TCOnew_test_suite/auto_tco.jsonnet.golden— expected outputBenchmark Results
Expected Impact
tail_callbenchmark: direct improvement (deeper recursion without stack overflow)inheritance_function_recursion: may benefit from TCO on recursive inheritance patternsrealistic2: depends on recursion depth in the workloadJMH — Pending Data
Analysis
if/elsebranches,localbindings, and direct self-recursion. Mutual recursion is out of scope.TailCall.resolve) is already battle-tested in the existing manual TCO path.TailCallinfrastructure. The static optimizer detects cases that users would otherwise need to manually optimize.References
TailCallmechanism insjsonnet/src/sjsonnet/Val.scalaResult
Automatic tail-call optimization for self-recursive Jsonnet functions. Eliminates StackOverflowError on deep recursion without source changes. Draft PR pending benchmark data.