Arc Forumnew | comments | leaders | submitlogin
6 points by absz 6000 days ago | link | parent

It sounds like that should work: change the xdef of eval to

  (xdef 'eval (lambda (expr) (arc-prim-eval (ac-denil expr))))
, and then change arc-eval to

  (define (arc-prim-eval expr)
    (eval (ac expr '()) (interaction-environment)))
  
  (define (arc-eval expr) 
    ((eval '__eval) expr))
. The xdef should come soon enough to prevent something from calling a non-existent eval. Then, in Arc, you should be able to do

  (redef eval (expr)
    (prn " - debug - " expr)
    (old expr))
or whatever. Let me test that...

...

...yes, this works! Well, almost. I didn't really test it, but (a) ordinary things seem to get evaluated fine, and (b) the message is printed. It doesn't seem to hit everything in a macro-expansion, but I can't tell whether or not it should. For instance, I get (output reformatted for clarity)

  arc> (mac do+ (a b) `(do (prn ,a) (prn ,b) (+ ,a ,b)))
   - debug - (mac do+ (a b) `(do (prn ,a) (prn ,b) (+ ,a ,b)))
   - debug - (input-history-update
               (mac do+ (a b) `(do (prn ,a) (prn ,b) (+ ,a ,b))))
   - debug - (output-history-update
               (quote #(tagged mac #<procedure>)))
  #3(tagged mac #<procedure>)
  arc> (do+ 1 2)
   - debug - (do+ 1 2)
  1
  2
   - debug - (input-history-update (quote (do+ 1 2)))
   - debug - (output-history-update (quote 3))
  3
. (Of course, its output didn't have extra line breaks and had quasiquote instead of `, etc.) I feel like it should print

   - debug - (do (prn 1) (prn 2) (+ 1 2))
too.

<EDIT>

The problem is that ac-mac-call calls ac directly so that it can pass the current environment as a second argument. Perhaps arc-eval should take an optional environment argument too? But that would clutter things unnecessarily on the Arc side... anyway, the point is, after looking at it for all of five minutes, macros are tricky. (And I haven't even looked at ac-macex yet...) For instance, a simple test:

  arc> (nil 1 2)
  Error: "string-ref: index 0 out of range for empty string"
  arc> (redef eval (expr)
         (if (and (cons? expr) (~car expr))
           (cdr expr)
           (old expr)))
  #<procedure: eval>
  arc> (nil 1 2)
  (1 2)
  arc> (mac donil (a b) `(nil ,a ,b))
  #3(tagged mac #<procedure>)
  arc> (donil 1 2) ; Should return (1 2), but:
  Error: "string-ref: index 0 out of range for empty string"
</EDIT>

The downside is that, if it isn't slow now, it might well prohibit certain optimizations (though reading Steve Yegge's recent talk makes me think that I might well be wrong). Is this worth pushing on Anarki?