The story of E, part 2 (fwd)

Ka-Ping Yee ping@lfw.org
Fri, 9 Oct 1998 04:34:22 -0700 (PDT)


More forwarded correspondence...


Ping                                            Talk back to the Web!
<ping@lfw.org>                                       http://crit.org/

---------- Forwarded message ----------
Date: Wed, 07 Oct 1998 13:54:36 -0700
From: "Mark S. Miller" <markm@caplet.com>
To: Ka-Ping Yee <ping@lfw.org>
Subject: Re: The story of E, part 2 (fwd)

Hey how about Part 1?  Looks good, nits below.


At 12:47 AM 10/7/98 -0700, Ka-Ping Yee wrote:
>... think of it as a dress rehearsal for the sections i
>might eventually like to write.

Have you seen http://www.erights.org ?  It would be useful there almost
immediately.


>Context is for someone familiar with C++ and currently
>learning Python -- which might be a decent trial run since
>many of your readers will probably be starting from somewhere
>similar, at least in the C++ camp.

Yup, but do you think the same text might also be accessible to someone
coming from Python with no C++?  Or someone coming from Java to Python?  Or...


>Capability-based security is actually a very simple concept.
>(Much simpler and cleaner than ACLs, which involve a list of
>permitted users on each object, like the file permissions in
>Unix.)  In a very small nutshell, capability-based security
>is just pure object-oriented programming.  That means, you
>get to call methods on an object *only* if you have a pointer
>to the object, and you can get that pointer to the object
>*only* if either (a) you created it or (b) someone passed it
>to you.  Once you make *everything* work that way, it becomes
>very easy to predict who cannot possibly do what.

Actually, there is a third case, as documented in
http://www.erights.org/doc/elib/elibmanual.pdf in chapter "Capability
Semantics" section #2 and demonstrated by your: 

>    define VectorMaker(x, y) {
>        define vector {
>            to toString { "<Vector " + x + ", " + y + ">" }
>            to getX { x }
>            to getY { y }
>            to getLength { sqrt(x*x + y*y) }
>        }
>    }

The new vector has access to x and y because it was created by someone
(VectorMaker) to have this access, and VectorMaker already had this access.



>And that's all.  Apply that to classic security problems,
>build a distributed object system that transfers objects
>over encrypted channels, and you have the core of what EC
>built.  

Transfers object references.  Objects are usually stationary.


>EC needed a language to build this in, and they
>decided that C++ was too hairy -- they wanted Java, but
>Java had lots of security holes introduced by the people
>at Sun, who -- although they got fairly close to a pure
>object model -- still were shortsighted in a few ways.  So
>the EC people made some modifications to Java to fix the
>holes and provide themselves some conveniences for talking
>to remote objects, and called the resulting language E.

Historically correct, but this describes what we now call "Original E" or
"The E Extensions to Java"
http://www.communities.com/products/tools/e/e_white_paper.html but not what
we now call E.  E is currently only implemented in Java, and leverages the
Java libraries, but it is not a modification of Java.



>... It took me a while to really
>get it all, but they're very cool ideas.

Thanks!  Do you remember which ideas you had trouble with?


>    ? 3 + 5
>    # result: 8

That's "# value: 8"


>There is also a short-hand for writing functions that may look
>more familiar:
>
>    define abs(x) {
>        if (x > 0) { x } else { -x }
>    }

Very nice example.


>    define VectorMaker(x, y) {
>        define vector {
>            to toString { "<Vector " + x + ", " + y + ">" }
>            to getX { x }
>            to getY { y }
>            to getLength { sqrt(x*x + y*y) }
>        }
>    }

Somewhere else, this example could also be rev'ed to show quasi-literals:

             to toString { `<Vector $x, $y>` }

It is possible but silly to make "sqrt" a standalone function in scope.
Instead, E floating point numbers already respond to a "sqrt" message, so
the following works:

	(x*x + y*y) doubleValue sqrt

"doubleValue" in the unfortunately named method inherited from Java to get
the value of this number as an IEEE double-precision floating point.  I'm
open to suggested renamings.  Btw, 

	(x**2 + y**2) doubleValue sqrt

is equivalent.


>    ? v getX()
>    # result: 1.5
>
>    ? v getY()
>    # result: 4
>
>    ? v getLength()
>    # result: 4.27200187265877

Equivalent but prettier:

    ? v getX
    # result: 1.5

    ? v getY
    # result: 4

    ? v getLength
    # result: 4.27200187265877

>...Because
>Mark wanted E to be easy to type as a command language as well
>as something you could edit and compile large programs in,...

Which is also why you can leave out the "()" above.


>... Well, you can still do this in E if you want:
>
>    define AnotherVectorMaker(initx, inity) {
>        define vector {
>            define x := initx
>            define y := inity
>
>            to toString { "<Vector " + x + ", " + y + ">" }
>            to getX { x }
>            to getY { y }
>            to getLength { sqrt(x*x + y*y) }
>        }
>    }


No you can't, because you can only define behavior, not state, between the
curlies following "define vector".  However, perhaps the following code
gets your point across:

>    define AnotherVectorMaker(initx, inity) {
>        define x := initx
>        define y := inity
>
>        define vector {
>            to toString { "<Vector " + x + ", " + y + ">" }
>            to getX { x }
>            to getY { y }
>            to getLength { sqrt(x*x + y*y) }
>        }
>    }
>
>This is actually pretty important to writing predictably secure
>programs: at one glance, just by looking at the definition of a
>class like the one above, you can see all the ways that any of
>the object's local data could ever get modified or exposed to
>the outside world.  The local scope ensures that the contents
>cannot be accessible from anywhere else -- you can be confident
>that any secrets you want to keep inside the object are safe.

Nice explanation.


>Like Python, E has built-in list and dictionary types.  You can
>create lists using the square brackets, and dictionaries using
>the curly-braces:
>
>    ? a := [1, 5, 4]
>    # result: [1, 5, 4]
>
>    ? a[0]
>    # result: 1
>
>    ? a[2]
>    # result: 4
>
>    ? a[3]
>    # problem: java.lang.ArrayIndexOutOfBoundsException
>
>    ? n := {"a" => 440, "b" => 493, "c" => 523 }
>    # result: {"a" => 440, "b" => 493, "c" => 523 }

Actually, in light of our previous conversation, I've decided to withdraw
the "hide" keyword from the language, use bare curlies for the hide
construct, and not have direct syntactic support for mappings (what you
call dictionaries).  Instead, syntactic support for mappings will be
provided by the quasiparser "map":

     ? n := map`{${"a"} => ${440}, ${"b"} => ${493}, ${"c"} => ${523}}`

Well, this change isn't yet implemented, and the above example demonstrates
that it might suck.  Back to the drawing board.


The rest looks fine.


Btw, your reference-state transition diagram is now at
http://erights.org/doc/elib/elibmanual.pdf in the section "Reference
Mechanics".


	Cheers,
	--MarkM