[e-lang] Announcing E-on-Common-Lisp (was Re: Is send DeepFrozen?)
Kevin Reid
kpreid at attglobal.net
Sun Dec 12 15:48:53 EST 2004
On Dec 12, 2004, at 14:36, Dean Tribble wrote:
>
>> So far I have implemented almost the entire Kernel-E language (except
>> for escape-catch and meta.getState()) via translation to CL, and
>> enough of ELib to run interesting code (though no IO as yet).
>
> There were two drivers led to using Squeak as my target (first for
> Joule and now E), and I'm wondering how you address them: "big
> integers" and "everything is an object". These were already
> properties of Smalltalk, so I get them almost for free.
> Big integers: Smalltalk directly implements arbitrarily large
> integers. Common Lisp may as well, but that leads to the second issue
>
> Everything is an object: Since any particular argument might be an
> integer (arbitrary precision) or might be an object of some flavor
> (e.g., user-defined integer, Promise, remote reference), it would seem
> you need to implement type tests all over the place. In particular,
> integers are not polymorphic with closures (which are presumably used
> for objects?) and so message sending needs to check whether it is to a
> primitive integer. How do you handle that? (e.g., are integers
> boxed?)
Common Lisp does have an "everything is a value/reference/object" model
(everything is of (a subtype of) type T), including for large and small
integers. There is no visible (un)boxing.
However, it has no single-dispatch message system. I implement this
myself (as does E-on-Java), with a CLOS generic function:
(defgeneric e-call-dispatch (receiver mverb &rest args))
For objects which are either of standard CL types (integers, floats,
vectors, etc.) I have a mechanism for defining the methods for that
type, again using CLOS dispatch.
For objects implemented in the E language, as well as ones which are
part of my implementation and are most readily implemented this way, I
define them as closures.
(defmethod e-call-dispatch ((recip function) mverb &rest args)
(apply recip mverb args))
For example, the primitive __loop object is defined by:
(e-named-lambda "org.erights.e.elang.interp.Loop"
:stamped +deep-frozen-stamp+
(:|__printOn/1| (tw)
(e-coercef tw +the-text-writer-guard+)
(e. tw |print| "<__loop>")
nil)
(:|run/1| (body)
(loop until (not (e-is-true (e. body |run|))))))
The e-named-lambda macro expands to, in part:
(lambda (mverb &rest args)
(case mverb
((:|__printOn/1|)
(destructuring-bind (tw) args
(setf tw (e-coerce tw +the-text-writer-guard+))
(e-call-dispatch tw :|print/1| "<__loop>")
nil))
((:|run/1|)
(destructuring-bind (body) args
(loop until (not (e-is-true (e-call-dispatch body
:|run/0|))))))))
I have omitted the details related to auditing and miranda methods.
Later I may add optimizations to translation to directly call
function-e-objects when they are known to be such.
(Not quite) the Common Lisp specification:
http://www.lispworks.com/reference/HyperSpec/Front/index.htm
--
Kevin Reid <http://homepage.mac.com/kpreid/>
More information about the e-lang
mailing list