It's optional because it has to do something that in a non-trivial implementation of ephemerons, such as Racket's, can't always be done.  If you need reference barriers, your code willl not be portable to all R7RS-large implementations, which is a pity, but there it is.

Is it a hard fact that it may be non-trivial to implement `reference-barrier' for a given proper implementation of ephemerons?

On the other hand, how do you want to code safely without `reference-barrier'?

Consider the following "implementation" of a weak-table:

(define table (make-vector 10))
(define count 0)

(define (store! key datum)
  (vector-set! table count (make-ephemeron key datum))
  (set! count (+ 1 count)))

(define (ref key)
  (let loop ((i 0))
    (if (= i count)
(error "not found" key)
(let ((ephemeron (vector-ref table i)))
 (let ((k (ephemeron-key ephemeron))
(d (ephereron-datum ephemeron)))
   (if (or (ephemeron-broken? ephemeron)
   (not (eq? key k)))
(loop (+ 1 i))
d))))))

Given this implementation, the following should evaluate to `foo':

(let ((key (vector 42)))
  (store! key 'foo)
  (ref key))

However, the following can happen: The Scheme implementation notices that key is no longer referenced after the application `(ref key)', so it can decide to GC the key after `(eq? key k)` is evaluated. This test is side-effect free, so the implementation (which may be a highly optimising compliler) may even reorder the program as follows:

(define (ref key)
  (let loop ((i 0))
    (if (= i count)
(error "not found" key)
(let ((ephemeron (vector-ref table i)))
  (let ((k (ephemeron-key ephemeron))
(d (ephereron-datum ephemeron)))
            (let ((test (not (eq? key k))))
      (if (or (ephemeron-broken? ephemeron)
       test))
(loop (+ 1 i))
d)))))))

But now, key can already be GCed before the test whether the ephemeron is broken takes place. Thus `(ref key)' can result in an error instead of evaluating to `foo'.

With `reference-barrier', the program can be corrected as follows:

(define (ref key)
  (let loop ((i 0))
    (if (= i count)
(error "not found" key)
(let ((ephemeron (vector-ref table i)))
  (let ((k (ephemeron-key ephemeron))
(d (ephereron-datum ephemeron)))
    (if (or (ephemeron-broken? ephemeron)
    (not (eq? key k)))
(loop (+ 1 i))
                (begin (reference-barrier key)
d)))))))

--

Marc 


We'll take up the question of new feature flags near the end of the process.  `reference-barriers` is a good candidate for one.

-- 
John Cowan          http://www.ccil.org/~cowan        xxxxxx@ccil.org
We want more school houses and less jails; more books and less arsenals;
more learning and less vice; more constant work and less crime; more
leisure and less greed; more justice and less revenge; in fact, more of
the opportunities to cultivate our better natures.  --Samuel Gompers