From ce2790d6f994fe1de50e63aaf9c0b9cb071bec00 Mon Sep 17 00:00:00 2001 From: Denis Buzdalov Date: Sun, 23 Jun 2024 15:39:32 +0300 Subject: [PATCH] [ perf ] Use alternative better GC on chez --- CHANGELOG_NEXT.md | 2 ++ src/Compiler/Scheme/Chez.idr | 40 +++++++++++++++++++++++++++++++-- src/Compiler/Scheme/ChezSep.idr | 2 +- 3 files changed, 41 insertions(+), 3 deletions(-) diff --git a/CHANGELOG_NEXT.md b/CHANGELOG_NEXT.md index a5e69e3c98..5bb98e3c15 100644 --- a/CHANGELOG_NEXT.md +++ b/CHANGELOG_NEXT.md @@ -115,6 +115,8 @@ This CHANGELOG describes the merged but unreleased changes. Please see [CHANGELO evaluated. Now when a delayed expression is lifted by CSE, it is compiled using Scheme's `delay` and `force` to memoize them. +* More efficient `collect-request-handler` is used. + #### Racket * Fixed CSE soundness bug that caused delayed expressions to sometimes be eagerly diff --git a/src/Compiler/Scheme/Chez.idr b/src/Compiler/Scheme/Chez.idr index 999e2d1ec2..d01b28e536 100644 --- a/src/Compiler/Scheme/Chez.idr +++ b/src/Compiler/Scheme/Chez.idr @@ -449,6 +449,42 @@ startChezWinSh chez appdir target progType = """ "\{ chez }" \{ progType } "$DIR/\{ target }" "$@" """ +-- This handler turned out to be much more effective than the original simple +-- `(collect-request-handler (lambda () (collect) (blodwen-run-finalisers)))` +export +collectRequestHandler : Builder +collectRequestHandler = """ + (collect-request-handler + (let* ([gc-counter 1] + [log-radix 2] + [radix-mask (sub1 (bitwise-arithmetic-shift 1 log-radix))] + [major-gc-factor 2] + [trigger-major-gc-allocated (* major-gc-factor (bytes-allocated))]) + (lambda () + (cond + [(>= (bytes-allocated) trigger-major-gc-allocated) + ;; Force a major collection if memory use has doubled + (collect (collect-maximum-generation)) + (blodwen-run-finalisers) + (set! trigger-major-gc-allocated (* major-gc-factor (bytes-allocated)))] + [else + ;; Imitate the built-in rule, but without ever going to a major collection + (let ([this-counter gc-counter]) + (if (> (add1 this-counter) + (bitwise-arithmetic-shift-left 1 (* log-radix (sub1 (collect-maximum-generation))))) + (set! gc-counter 1) + (set! gc-counter (add1 this-counter))) + (collect + ;; Find the minor generation implied by the counter + (let loop ([c this-counter] [gen 0]) + (cond + [(zero? (bitwise-and c radix-mask)) + (loop (bitwise-arithmetic-shift-right c log-radix) + (add1 gen))] + [else + gen]))))])))) + """ + ||| Compile a TT expression to Chez Scheme compileToSS : Ref Ctxt Defs -> Bool -> -- profiling @@ -480,7 +516,7 @@ compileToSS c prof appdir tm outfile , fromString support , fromString extraRuntime , code - , "(collect-request-handler (lambda () (collect) (blodwen-run-finalisers)))\n" + , collectRequestHandler ++ "\n" , main , schFooter prof True ] @@ -525,7 +561,7 @@ compileToSSInc c mods libs appdir tm outfile fromString support ++ concat loadlibs ++ concat loadsos ++ - "(collect-request-handler (lambda () (collect) (blodwen-run-finalisers)))\n" ++ + collectRequestHandler ++ "\n" ++ main ++ schFooter False False Right () <- coreLift $ writeFile outfile $ build scm diff --git a/src/Compiler/Scheme/ChezSep.idr b/src/Compiler/Scheme/ChezSep.idr index 36be17484e..3005220b0d 100644 --- a/src/Compiler/Scheme/ChezSep.idr +++ b/src/Compiler/Scheme/ChezSep.idr @@ -237,7 +237,7 @@ compileToSS c chez appdir tm = do main <- schExp empty (Chez.chezExtPrim empty) Chez.chezString 0 ctm Core.writeFile (appdir "mainprog.ss") $ build $ sepBy "\n" [ schHeader (map snd libs) [lib.name | lib <- chezLibs] - , "(collect-request-handler (lambda () (collect) (blodwen-run-finalisers)))" + , collectRequestHandler , main , schFooter ]