 
 ;;;; Forward Mode
 
-(declare forward-transform)
-
-(defprotocol Interleavable
-  (interleave-bundle [primal tangent]))
+(declare forward-transform interleave-bundle)
 
 (defrecord bundle [primal tangent]
   Applicable
-  (jl-apply [self arg] (jl-apply (forward-transform (interleave-bundle primal tangent))
-				 arg)))
+  (jl-apply [self arg]
+   (jl-apply (forward-transform (interleave-bundle primal tangent)) arg)))
 
 (defn make-bundle [primal tangent]
   (new bundle primal tangent))
 
-(extend-type pair
-  Interleavable
-  (interleave-bundle [primal tangent] (new pair (make-bundle (:car primal) (:car tangent))
-					   (make-bundle (:cdr primal) (:cdr tangent)))))
-
-(extend-type closure
-  Interleavable
-  ;; TODO Get the constants from the body of the tangent
-  (interleave-bundle
-   [primal tangent]
-   (new closure (:formal primal) (:body primal)
-	(interleave-env (:env primal) (:env tangent)))))
-
-(extend-type primitive
-  Interleavable
-  (interleave-bundle [primal tangent] primal))
+(defn interleave-bundle [primal tangent]
+  (cond (pair? primal)
+	(new pair (make-bundle (:car primal) (:car tangent))
+	     (make-bundle (:cdr primal) (:cdr tangent)))
+	(closure? primal)
+	;; TODO Get the constants from the body of the tangent
+	(new closure (:formal primal) (:body primal)
+	     (interleave-env (:env primal) (:env tangent)))
+	(primitive? primal)
+	primal))
 
 (defn forward-transform [thing]
   (if (contains? (meta thing) :forward)

  (jl-eval [self env]))

(defrecord variable [name]
  JLObject
  (variable? [self] true)
  Evaluable
  (jl-eval [self env] (lookup env name))

(defn jl-do [form]
  (jl-eval (syntax form) inital-env))

; (jl-eval (syntax-body (sexp-slurp (clojure.java.io/file "foo.jlad"))) inital-env)
