env.scm 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106
  1. ; Copyright (c) 1993-2008 by Richard Kelsey and Jonathan Rees. See file COPYING.
  2. ; Accessing packages
  3. (define (environment-ref package name)
  4. (carefully (package-lookup package name)
  5. (lambda (loc)
  6. (if (location-assigned? loc)
  7. (contents loc)
  8. (error "uninitialized variable" name package)))
  9. package
  10. name))
  11. (define (environment-set! package name value)
  12. (let ((binding (package-lookup package name)))
  13. (if (and (binding? binding)
  14. (not (variable-type? (binding-type binding))))
  15. (error "invalid assignment" name package value)
  16. (carefully binding
  17. (lambda (loc)
  18. (set-contents! loc value))
  19. package name))))
  20. (define (environment-define! package name value)
  21. (set-contents! (package-define! package name usual-variable-type #f #f)
  22. value))
  23. (define (*structure-ref struct name)
  24. (let ((binding (structure-lookup struct name #f)))
  25. (if binding
  26. (carefully binding contents struct name)
  27. (error "structure-ref: name not exported" struct name))))
  28. (define (carefully binding action env name)
  29. (cond ((not binding)
  30. (error "unbound variable" name env))
  31. ((not (binding? binding))
  32. (error "peculiar binding" binding name env))
  33. ((eq? (binding-type binding) syntax-type)
  34. (error "attempt to reference syntax as variable" name env))
  35. (else
  36. (let ((loc (binding-place binding)))
  37. (if (location? loc)
  38. (if (location-defined? loc)
  39. (action loc)
  40. (error "unbound variable" name env))
  41. (error "variable has no location" name env))))))
  42. ; Interaction environment
  43. (define $interaction-environment (make-fluid (make-cell #f)))
  44. (define (interaction-environment)
  45. (fluid-cell-ref $interaction-environment))
  46. (define (set-interaction-environment! p)
  47. (if (package? p)
  48. (fluid-cell-set! $interaction-environment p)
  49. (call-error "invalid package" set-interaction-environment! p)))
  50. (define (with-interaction-environment p thunk)
  51. (if (package? p)
  52. (let-fluid $interaction-environment (make-cell p) thunk)
  53. (call-error "invalid package" with-interaction-environment p)))
  54. ; Scheme report environment. Should be read-only; fix later.
  55. (define (scheme-report-environment n)
  56. (if (= n *scheme-report-number*)
  57. *scheme-report-environment*
  58. (error "no such Scheme report environment")))
  59. (define *scheme-report-environment* #f)
  60. (define *null-environment* #f)
  61. (define *scheme-report-number* 0)
  62. (define (set-scheme-report-environment! repnum env)
  63. (set! *scheme-report-number* repnum)
  64. (set! *scheme-report-environment* env)
  65. (set! *null-environment* env)) ; A cheat.
  66. (define (null-environment n)
  67. (if (= n *scheme-report-number*)
  68. *null-environment*
  69. (error "no such Scheme report environment")))
  70. ; Make an infinite tower of packages for syntax.
  71. ; structs should be a non-null list of structures that should be
  72. ; opened at EVERY level of the tower.
  73. (define (make-reflective-tower eval structs id)
  74. (let recur ((level 1))
  75. (delay (cons eval
  76. (make-simple-package structs
  77. eval
  78. (recur (+ level 1))
  79. `(for-syntax ,level ,id))))))
  80. ; (set-reflective-tower-maker! p (lambda (clauses id) ...))
  81. ; where clauses is a list of DEFINE-STRUCTURE clauses
  82. (define set-reflective-tower-maker!
  83. (let ((name (string->symbol ".make-reflective-tower.")))
  84. (lambda (p proc)
  85. (environment-define! p name proc))))