home *** CD-ROM | disk | FTP | other *** search
/ MacFormat 1994 November / macformat-018.iso / Utility Spectacular / Developer / macgambit-20-compiler-src-p2 / Thomas / poplat.scm < prev    next >
Encoding:
Text File  |  1994-07-26  |  5.5 KB  |  155 lines  |  [TEXT/gamI]

  1. ; -*-Scheme-*-
  2. ;
  3. ; $Id: gambit_poplat.scm,v 1.1 1992/09/22 20:56:57 birkholz Exp $
  4. ;
  5. ; Copyright (c) 1988 Massachusetts Institute of Technology
  6. ;
  7. ; This material was developed by the Scheme project at the Massachusetts
  8. ; Institute of Technology, Department of Electrical Engineering and
  9. ; Computer Science.  Permission to copy this software, to redistribute
  10. ; it, and to use it for any purpose is granted, subject to the following
  11. ; restrictions and understandings.
  12. ;
  13. ; 1. Any copy made of this software must include this copyright notice
  14. ; in full.
  15. ;
  16. ; 2. Users of this software agree to make their best efforts (a) to
  17. ; return to the MIT Scheme project any improvements or extensions that
  18. ; they make, so that these may be included in future releases; and (b)
  19. ; to inform MIT of noteworthy uses of this software.
  20. ;
  21. ; 3. All materials developed as a consequence of the use of this
  22. ; software shall duly acknowledge such use, in accordance with the usual
  23. ; standards of acknowledging credit in academic research.
  24. ;
  25. ; 4. MIT has made no warrantee or representation that the operation of
  26. ; this software will be error-free, and MIT is under no obligation to
  27. ; provide any services, by way of maintenance, update, or otherwise.
  28. ;
  29. ; 5. In conjunction with products arising from the use of this material,
  30. ; there shall be no use of the name of the Massachusetts Institute of
  31. ; Technology nor of any adaptation thereof in any advertising,
  32. ; promotional, or sales literature without prior written consent from
  33. ; MIT in each case.
  34.  
  35. ; This file requires the following non-IEEE primitives:
  36.  
  37. ; ##weak-pair?, ##weak-cons, ##weak-car, ##weak-cdr, ##weak-set-cdr! for
  38. ; manipulating "weak-cons cells," whose cdr is normal but whose car
  39. ; turns to #F during a garbage collection if no non-weak references
  40. ; are found to the object in the car.
  41.  
  42. ; ##add-gc-finalize-job registers a thunk (procedure of no arguments) to be
  43. ; called after each garbage collection is complete and before Scheme resumes
  44. ; running.
  45.  
  46. ;;;; Populations
  47.  
  48. ;;; A population is a collection of objects.  This collection has the
  49. ;;; property that if one of the objects in the collection is reclaimed
  50. ;;; as garbage, then it is no longer an element of the collection.
  51.  
  52. (define (initialize-population-package!)
  53.   (set! population-of-populations (##weak-cons population-tag '()))
  54.   (##add-gc-finalize-job ; setup GC finalization
  55.     gc-all-populations!))
  56.  
  57. (define bogus-false '(BOGUS-FALSE))
  58. (define population-tag '(POPULATION))
  59.  
  60. (define (canonicalize object)
  61.   (if (eq? object #f) bogus-false object))
  62.  
  63. (define (uncanonicalize object)
  64.   (if (eq? object bogus-false) #f object))
  65.  
  66. (define (gc-population! population)
  67.   (let loop ((l1 population) (l2 (##weak-cdr population)))
  68.     (cond ((null? l2) #t)
  69.       ((eq? (##weak-car l2) #f)
  70.        (##weak-set-cdr! l1 (##weak-cdr l2))
  71.        (loop l1 (##weak-cdr l1)))
  72.       (else (loop l2 (##weak-cdr l2))))))
  73.  
  74. (define (gc-all-populations!)
  75.   (gc-population! population-of-populations)
  76.   (map-over-population! population-of-populations gc-population!))
  77.  
  78. (define population-of-populations #f)
  79.  
  80. (define (make-population)
  81.   (let ((population (##weak-cons population-tag '())))
  82.     (add-to-population! population-of-populations population)
  83.     population))
  84.  
  85. (define (population? object)
  86.   (and (##weak-pair? object)
  87.        (eq? (##weak-car object) population-tag)))
  88.  
  89. (define (add-to-population! population object)
  90.   (let ((object (canonicalize object)))
  91.     (let loop ((previous population) (this (##weak-cdr population)))
  92.       (if (null? this)
  93.       (##weak-set-cdr! population
  94.                (##weak-cons object (##weak-cdr population)))
  95.       (let ((entry (##weak-car this))
  96.         (next (##weak-cdr this)))
  97.         (cond ((not entry)
  98.            (##weak-set-cdr! previous next)
  99.            (loop previous next))
  100.           ((not (eq? object entry))
  101.            (loop this next))))))))
  102.  
  103. (define (remove-from-population! population object)
  104.   (let ((object (canonicalize object)))
  105.     (let loop ((previous population) (this (##weak-cdr population)))
  106.       (if (not (null? this))
  107.       (let ((entry (##weak-car this))
  108.         (next (##weak-cdr this)))
  109.         (if (or (not entry) (eq? object entry))
  110.         (begin (##weak-set-cdr! previous next)
  111.                (loop previous next))
  112.         (loop this next)))))))
  113.  
  114. ;;;; Higher level operations
  115.  
  116. (define (map-over-population population procedure)
  117.   (let loop ((l1 population) (l2 (##weak-cdr population)))
  118.     (cond ((null? l2) '())
  119.       ((eq? (##weak-car l2) #f)
  120.        (##weak-set-cdr! l1 (##weak-cdr l2))
  121.        (loop l1 (##weak-cdr l1)))
  122.       (else
  123.        (cons (procedure (uncanonicalize (##weak-car l2)))
  124.          (loop l2 (##weak-cdr l2)))))))
  125.  
  126. (define (map-over-population! population procedure)
  127.   (let loop ((l1 population) (l2 (##weak-cdr population)))
  128.     (cond ((null? l2) #t)
  129.       ((eq? (##weak-car l2) #f)
  130.        (##weak-set-cdr! l1 (##weak-cdr l2))
  131.        (loop l1 (##weak-cdr l1)))
  132.       (else
  133.        (procedure (uncanonicalize (##weak-car l2)))
  134.        (loop l2 (##weak-cdr l2))))))
  135.  
  136. (define (for-all-inhabitants? population predicate)
  137.   (let loop ((l1 population) (l2 (##weak-cdr population)))
  138.     (or (null? l2)
  139.     (if (eq? (##weak-car l2) #f)
  140.         (begin (##weak-set-cdr! l1 (##weak-cdr l2))
  141.            (loop l1 (##weak-cdr l1)))
  142.         (and (predicate (uncanonicalize (##weak-car l2)))
  143.          (loop l2 (##weak-cdr l2)))))))
  144.  
  145. (define (exists-an-inhabitant? population predicate)
  146.   (let loop ((l1 population) (l2 (##weak-cdr population)))
  147.     (and (not (null? l2))
  148.      (if (eq? (##weak-car l2) #f)
  149.          (begin (##weak-set-cdr! l1 (##weak-cdr l2))
  150.             (loop l1 (##weak-cdr l1)))
  151.          (or (predicate (uncanonicalize (##weak-car l2)))
  152.          (loop l2 (##weak-cdr l2)))))))
  153.  
  154. (initialize-population-package!)
  155.