self-references.scm 3.0 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980
  1. ;;; Continuation-passing style (CPS) intermediate language (IL)
  2. ;; Copyright (C) 2013-2019 Free Software Foundation, Inc.
  3. ;;;; This library is free software; you can redistribute it and/or
  4. ;;;; modify it under the terms of the GNU Lesser General Public
  5. ;;;; License as published by the Free Software Foundation; either
  6. ;;;; version 3 of the License, or (at your option) any later version.
  7. ;;;;
  8. ;;;; This library is distributed in the hope that it will be useful,
  9. ;;;; but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. ;;;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. ;;;; Lesser General Public License for more details.
  12. ;;;;
  13. ;;;; You should have received a copy of the GNU Lesser General Public
  14. ;;;; License along with this library; if not, write to the Free Software
  15. ;;;; Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
  16. ;;; Commentary:
  17. ;;;
  18. ;;; A pass that replaces free references to recursive functions with
  19. ;;; bound references.
  20. ;;;
  21. ;;; Code:
  22. (define-module (language cps self-references)
  23. #:use-module (ice-9 match)
  24. #:use-module ((srfi srfi-1) #:select (fold))
  25. #:use-module (language cps)
  26. #:use-module (language cps utils)
  27. #:use-module (language cps intmap)
  28. #:use-module (language cps intset)
  29. #:export (resolve-self-references))
  30. (define* (resolve-self-references cps #:optional (label 0) (env empty-intmap))
  31. (define (subst var)
  32. (intmap-ref env var (lambda (var) var)))
  33. (define (rename-exp exp)
  34. (rewrite-exp exp
  35. ((or ($ $const) ($ $prim)) ,exp)
  36. (($ $call proc args)
  37. ($call (subst proc) ,(map subst args)))
  38. (($ $callk k proc args)
  39. ($callk k (subst proc) ,(map subst args)))
  40. (($ $primcall name param args)
  41. ($primcall name param ,(map subst args)))
  42. (($ $values args)
  43. ($values ,(map subst args)))))
  44. (define (rename-term term)
  45. (rewrite-term term
  46. (($ $continue k src exp)
  47. ($continue k src ,(rename-exp exp)))
  48. (($ $branch kf kt src op param args)
  49. ($branch kf kt src op param ,(map subst args)))
  50. (($ $prompt k kh src escape? tag)
  51. ($prompt k kh src escape? (subst tag)))
  52. (($ $throw src op param args)
  53. ($throw src op param ,(map subst args)))))
  54. (define (visit-label label cps)
  55. (match (intmap-ref cps label)
  56. (($ $kargs _ _ ($ $continue k src ($ $fun label)))
  57. (resolve-self-references cps label env))
  58. (($ $kargs _ _ ($ $continue k src
  59. ($ $rec names vars (($ $fun labels) ...))))
  60. (fold (lambda (label var cps)
  61. (match (intmap-ref cps label)
  62. (($ $kfun src meta self)
  63. (resolve-self-references cps label
  64. (intmap-add env var self)))))
  65. cps labels vars))
  66. (($ $kargs names vars term)
  67. (intmap-replace! cps label
  68. (build-cont ($kargs names vars ,(rename-term term)))))
  69. (_ cps)))
  70. (intset-fold visit-label (compute-function-body cps label) cps))