ERights Home download 
Back to: E 0.8.13e Download and Install E 1st child: E 0.8.14b: Installing on Windows On to: E 0.8.15b Download and Install E

Download and Install
E 0.8.14b

Jump to

Download by Platforms & Versions
Highlights this Version

Variants and Subsets of E
New environment variable documentation!

Are you sure you want the 0.8.14b version?

Download by Platforms & Versions

Earlier versions of E have been tested and run on MSWindows (95, 98 FE, NT, 2K), Linux, and now Mac OS X (which I think is really a FreeBSD platform). It should run on other UNIX platforms as well, given an adequate version of Java and bash (see below). It should also run without problems on MSWindows 98 SE and on ME, but as far as we are aware, no one has tried this. If you experience any problems, or have any other informative experiences, please let me know, or report a bug.

The Installing links below describe how to install, and run various forms of the binary distribution. The Building links describe how to build E from the source release. The Download links will download each corresponding form of the release to your machine.

MSWindows 9x/ME/NT/2k
(zip files)
Unix & Unix-like Platforms
Now supporting Mac OS X!
(tar.gz files)


Highlights of this Version

Improved emacs mode for E

In the source distributions, the file e/src/elisp/e-mode.el is an emacs mode for E, originally written by Will Glozer (thanks!), and now improved by Darius Bacon (thanks!) and MarkM.

CapDesk Icon and Shortcut

CapDesk now has its own icon, ,originally contributed by Ka Ping Yee (thanks!) to the E project for other uses. On Windows, capDesk.e now has its own shortcut using this icon. Unfortunately, in reducing it to 32x32 and making it suitable for use against various backgrounds, I (MarkM) think I ruined it, so consider the current appearance of this icon a placeholder until someone with a working right hemisphere fixes it.

If no one objects, I'm thinking of retiring the old (e) shortcut for the "e --interact" command. This command is useful from a shell, but someone launching E by clicking on a shortcut would probably always click on(elmer) rather than . If this isn't true and you want this shortcut to stick around, please let me know now.

Simpler Manual Installation

I have gotten many complaints about the tediousness of the manual install procedure, because of the large number of properties in eprops.txt that need to be set to their default value. As the new eprops-template.txt (the file to be copied and edited into eprops.txt) say:

# NEW (as of 0.8.14b): To ease manual installation, some of the
# entries in the eprops-template.txt file list the default value as
# their value rather than a dollar-double-curly form.  After copying
# eprops-template.txt to eprops.txt, you don't need to edit these, but
# you may.

Thanks to everyone who complained about the way it used to be (too numerous to enumerate).

Thanks also to Ben Laurie for an improvement to e-template.txt (documented there) that makes it easier to install as well.

Class and delegate are deprecated. Long live extends!

Everyone has now had their chance to comment about the proposal by Dean Tribble (thanks!) documented by MarcS here, to add the extends keyword and construct to the language as a replacement both for delegate and class. Since no one has complained, and the proposal seems clearly good to me, as of 0.8.14b extends is now accepted as an official part of the language, and class and delegate are now officially deprecated. In this release, all three work by default, but are controlled by three separate props, e.enable.sub-object (for extends), e.enable.delegate-clause, and e.enable.class-expr, as documented in the new eprops.txt.

Better Miranda printOn and E Stack Traces

Thanks to complaints by Dean Tribble, and leveraging our recent implementation of fully qualified names for E object definitions, E's Miranda printOn method now prints starting at the last "significant" part of the object's fully qualified name. A "significant" name is anything other that "self" and that doesn't start with a digit. Start with a digit? A Java anonymous class and an E anonymous object both get local names which are numbers. The new rule seems to be a good balance between readability and brevity. In particular, it makes the stack traces spit out by E programs using anonymous functions and "self" much more useful. Why "self"? In Dean's pattern for using the new extends keyword for inheritance, one defines the concrete base object "self". I'll let Dean explain why.

Listening on many ears

This release integrates in changes from Chris Hibbert (thanks!) so that you can now instruct a vat to listen on multiple TCP/IP ports. You can do this using the API of NetConfig prior to going on the air, or using the properties as explained in the new eprops.txt:

# e.ListenAddressPath is the optional TCP/IP addresses at which this
# vat should create the sockets it listens to.  For each element, if
# an IP address isn't given, the socket defaults to listening on all
# IP addresses of this host.  If an IP address is given, it must be
# one of the IP addresses of this host.  If the TCP port isn't given,
# it defaults to 0.  A TCP port of 0 instructs the OS to pick any free
# TCP port.

# e.ListenAddressPath=

# e.ListenAddress is deprecated. If provided, this address is added
# to the end of e.ListenAddressPath

# e.ListenAddress=
I'll let Chris or Dean explain the need that motivated this feature.

The Changing of the Guards

In the thread rooted here, Terry Stanley proposes a set of naming conventions for naming variables, functions, and objects. These conventions have evolved some since then (eg, "Pass" has become "Rcvr"), but we have essentially been following the practices recommended there, with mixed results.

There has been a live controversy raging privately without resolution that we should now make public. Should we be encoding near (supports immediate calls) vs vow (successful resolution supports immediate calls) vs rcvr (just do eventual sends) in the names (as this thread recommends, and as we've been mostly doing since then), or should we instead, or in addition, be using our guard annotations to express these distinctions; as Terry now advocates (thanks!).

Whatever the resolution of this controversy, it seems like a good idea to be able to express these distinctions with guard annotations. This would be especially true if these guards could enforce the property they state, as with other guards. Unfortunately, for the new ":vow" and ":rcvr" guards, we can't enforce these properties at a reasonable cost until we have good support for PassByCopy, so these guards are just advisory for now. Nevertheless, as a way to capture programmer intent in a machine understandable form, this seems worth doing anyway. The relevant guards are:

  • :near - (No change in meaning or implementation.) A near reference passes this guard. All others get rejected. A near reference supports immediate calls on the object it designates. This guard is properly enforced.

  • :pbc - (No change in meaning or implementation.) A near reference to a PassByConstruction object. All PassByCopy objects are also PassByConstruction. When a pbc is passed as an argument, the value as received by the callee will be pbc. An unresolved reference to a pbc will successfully resolve only to a pbc, never to a far reference. This guard is properly enforced.

  • :vow and :vow(valueGuard) - (New as of 0.8.14.) A vow may itself be a near, unresolved, or broken reference. If it's currently unresolved, then its fulfillment (its successful resolution) must be near. In other words, its resolution must be near or broken, but never far. A possibly unresolved reference to a pbc is a vow. A ":vow(valueGuard)" is a vow for something that will pass the argument valueGuard. For example, a ":vow(integer)" is a vow for an integer.

    This guard is currently not enforced -- it is currently operationally equivalent to ":any" and is used purely for documentation purposes. Once it is enforced, it will send its argument valueGuard to the specimen's host to coerce the specimen there. If the specimen is remote, the valueGuard itself will have to be a pbc object. The ":vow(valueGuard)" will then return a promise for the result of (remotely) coercing the specimen by the valueGuard. This preserves pipelining (which a local check would lose), and prevents any messages from being delivered to a specimen that doesn't pass the valueGuard, but relies of the specimen's host to run the valueGuard honestly. If you want to trade pipelining for local enforcement, this is easy to write in the language, but seemed like the wrong default.

  • :rcvr and :rcvr(valueGuard) - (New as of 0.8.14.) A rcvr is a reference that may be eventual, and whose resolution may be far. Therefore, one should only deal with rcvrs using eventual sends -- never by immediate calls. Without an argument guard, ":rcvr" has the same operational meaning as ":any", and so is properly if vacuously enforced. ":rcvr(valueGuard)" is a reference for an object that will pass the argument valueGuard. As with ":vow(valueGuard)", this is currently unenforced, but will be enforced using the same technique documented above.

  • :any - (No change in meaning or implementation.) The specimen can be any kind of reference, and no coercion is performed (ie, coerce returns its argument). This guard is properly if vacuously enforced. Though there is no operational difference between this and ":rcvr", there is a documentation difference, and a possible difference in static checking rules (see below). Whereas ":rcvr" states that the declarer has special knowledge that he's warning his client of, ":any" is better used when the client may have better knowledge than the declarer. For example, a get/1 from a ConstList would be declared as ":any" rather than ":rcvr", since the declarer know that he's only handing back what was put in, which could be anything; whereas the client knows what he put in.

These annotations seem adequate for a lint-like static checking advisor. Here are some example rules that seem easy to automate. For concreteness, "integer" is used as an example of a pbc type, and a guard for such a type that does no coercion (either passes its argument through or complains), and "counter" is used as an example of a PassByProxy type and corresponding non-coercing guard. In the following "<=" means "subtype" and "=>" means "produces" or "is of type". Note: I am not a type theory kind of guy, so advice and corrections would be especially welcome.

  • near <= vow <= rcvr
  • integer <= vow(integer) <= rcvr(integer)
  • warn that rcvr(integer) should be vow(integer)
  • counter <= vow(counter) <= rcvr(counter)
  • warn that vow(counter) may want to be rcvr(counter), though vow(counter) can be correct if you know that the counter is necessarily local.
  • Given typedef f1():integer, f1() => integer, f1 <- () => vow(integer)
  • Given typedef f2():vow, f2() => vow, f2 <- () => vow (since f2 is a near reference to such a function)
  • Given f2Rcvr :rcvr(f2), f2Rcvr <- () => rcvr (since f2Rcvr may be remote, and a vow to it may be a rcvr to us.)
  • Given f1Rcvr :rcvr(f1), f1Rcvr <- () => vow(integer) (since a remote reference to a vow for a pbc is still a vow for a pbc.)
  • when (vow) -> done(near) is ok
  • when (vow(integer)) -> done(integer) is ok
  • when (rcvr) -> done(rcvr) is ok
  • Given typedef f3(integer), f3(integer) is ok, f3 <- (integer) is ok
  • Given typedef f4(counter), f4(counter) is ok, f4 <- (counter) is ok (since both f3 and counter are near references.)
  • Given f4Rcvr :rcvr(f4), f4Rcvr <- (counter) is bad (since f4Rcvr may be remote.)
  • Given counterRcvr :counter, warn of f4Rcvr <- (counterRcvr), since it's probably bad, but is sometimes necessary and appropriate if the programmer has special knowledge these are both resolved references into the same remote vat. I doubt we should try to capture such special knowledge in static checking rules.

This list is intended to be more suggestive than correct or complete, in the hopes that someone who has competency with such matters may take it from here. Please let me know if you're interested, or start an argument about these rules on the list.

Variants and Subsets of E

A complete E system is persistent, distributed, and capability-secure both within and between processes. Incomplete variants of E are tagged by which of these features are left out.

Feature Prefix if
feature is absent
What it stands for







capability security

capability security


Distributed Application Framework
Forsaking Encryption

A non-persistent E is called time-local since an object only exist as long as its hosting process does. A non-distributed E is called space-local if an object and all references to it only exist within its hosting process.

E by definition provides distributed capability-security -- the ability for objects in mutually suspicious processes to safely cooperate. If it looks like E and it quacks like E, it might be a duck; but if it doesn't provide distributed capability security, it's not E. A system that's otherwise equivalent to E, but doesn't provide distributed capability security, is called daffE. A distributed E can only be implemented by means of strong crypto, of course, for which we are using code derived from the Cryptix library (in accord with the terms of their open-source license). In a space-local system, no distributed insecurity can arise, so such a system would be an sl-E rather than an sl-daffE.

E is designed to provide local capabillity-security -- the ability for mutually suspicious objects hosted by the same process to safely cooperate, and the use of capability discipline to determine which of its hosting process's authorities it may exercise. Such objects could be executing untrusted code -- code that the hosting process (or its owner) doesn't need to fully trust.

This is a "complete" release of E. "complete" is in quotes, because both the persistence and the distribution leave much to be desired, as explained here. However, these are close enough that this release that doesn't need qualifiers in its name.


Versions & Types of Java

In refering to various versions of Java, we follow Sun's terminology and numbering. A Java Runtime, or jre, is adequate to run standard Java binary programs (class files & resources). A Java Development Kit, or jdk, is adequate both to build a program from sources and to run it. A jdk is a superset of the corresponding jre, and their version numbers are always in synch. Each successive version of the jdk/jre from Sun effectively defines a new version of the Java & JVM standards, except that Sun has introduced a numbering inconsistency: The Java/JVM 2.x standard corresponds to Sun's jdk/jre 1.2.x. We ignore this inconsistency and refer to both as 1.2.x.

This version of E requires a jre >= 1.3.1. E no longer supports Java < 1.3.1. To build E from sources, a corresponding jdk is required.

Note: E does not install correctly when using JDK1.4beta on Windows2000 -- it fails to exec with "winfo.exe" executable, used during install time to gather info about your Windows system. It seems to be a more general problem in execing executables. If you experience this problem, we suggest you install using a JDK1.3.*. Once installed, E should work fine with either JDK1.3.* or JDK1.4beta.
( Track this issue... )

Some places to get a jre or jdk:

Mac OS X
already included
already included


To build E requires a bash available as "/bin/bash". If bash is unavailable for your platform, it seems to work better than it should to make a symbolic link from "/bin/bash" to "/bin/sh". If you try this and run into problems, please report these problems.

To run the E driver script "e" requires a bash >= 2.01 available as "/bin/bash". The E driver script is required in order to be able to run E scripts (*.e files) directly as executables. To check your bash version, type


to your bash shell. A bash (2.05 as of this writing) for Mac OS X is available for download from Savage Transcendental Studios.

Build-Only Dependencies

If you are only installing E from a binary distribution, or only rebuilding the Java portion for your own use, you can ignore this section. However, if you wish to build an E distribution from sources, then you will need the equivalent of the following tools as well.

The Cygwin Distribution

The E building process relies on a number of UNIX tools. These are available for Windows from Cygnus Support as the Cygwin package. If you wish to build E on Windows, you should download and install a version >= 1.0.

BYacc/Java (Berkeley Yacc for Java)

The E source distribution contains the executable binary program byaccj.exe for Windows, and byaccj for Linux/386/glibc. These are actually BYacc/Java from Bob Jamison and others. BYacc/Java is the Berkeley Yacc program extended with a "-j" flag and others for producing Java output. BYacc/Java is covered by the Berkeley License. The sources to byaccj are bundled with the E sources, and byaccj is optionally made as part of making E.

BYacc/Java is only needed if you wish to remake the parsers as part of making E. Usually, this is only necessary of you wish to edit the *.y files in the source tree (term.y and e.y). Since BYacc/Java is a C program, it was causing porting headaches, and most people interested in rebuilding E won't need to rebuild the parsers anyway. So as of this release we added a switch: If you set the environment variable "MAKE_PARSERS" to "true" before running "make", then make will try to build BYacc/Java on your system, and then use it to rebuild the parsers. Otherwise, it will just use the parsers included in the source tree.

Zip Files

Our build process packs up the *.zip files in the distribution by using Info-Zip's highy portable, and highly ported, zip program. Info-Zip's zipping tools are open-sourced with a license that seems to resemble the X11 license, but before redistributing it, you should read it for yourself. The E distributions do not bundle in these tools.

Environment Variables

The following are the main environment variables controlling building, and normally the only ones you will need to be aware of if something goes wrong. Others variables are documented in the various makefiles, especially

  • OSTYPE - To determine whether we are compiling on the Cygwin platform, we check whether this is set to either "cygwin" or "cygwin32" (both have been encountered). If so, we set CYGWINOS to "1". All other conditionals test CYGWINOS.

  • CYGWINOS - See above. If you actually are on a Cygwin environment, but OSTYPE has yet a different value, you probably shouldn't change it for fear of screwing something else up. So just set CYGWINOS to "1" yourself.

  • JAVA_HOME - If set, it should be set to the directory where the JDK is installed. This is used to find certain executables and jar files that come with the JDK distribution.

    If not set, then the needed executables (eg, "java") are assumed to be on the PATH, and the jar files directly known to the makefiles are assumed to be adequate for building. This is known to work when compiling with javac, and known not to work when compiling with jikes 1.15. See below.

  • JAVAC - If set, should be set to executable for the Java compiler. The Java compiler is assumed to be command line compatible with javac or jikes. If the executable is on the PATH, then simple names (like "javac") can be used rather than full pathnames. This can also include some initial compiler options to appear before the others. I normally build with JAVAC set to "jikes +E +F". I'm using Jikes 1.15, and at least that version needs to be provided with the JDK's rt.jar file as an explicit component of the -classpath argument. The makefiles do this automatically if JAVA_HOME is set to the JDK's install directory.

    If not set, this defaults to either "javac" or "$(JAVA_HOME)/bin/javac", depending on whether JAVA_HOME is set.

  • JAVACMD - If set, should be set to an executable for running Java that's command-line compatible with the JDK's "java" executable.

    If not set, this defaults to either "java" or "$(JAVA_HOME)/jre/bin/java" depending on whether JAVA_HOME is set.

  • JAVADOC - If set, should be set to an executable for generating Javadoc documentation that's command-line compatible with the JDK's "javadoc" executable.

    If not set, this defaults to either "javadoc" or "$(JAVA_HOME)/bin/javadoc" depending on whether JAVA_HOME is set.

  • MAKE_PARSERS - E contains a small number (two as of this writing) of *.y files, which are compiled into parsers written in Java using BYacc/Java (see above). The generated parsers are included in the source distribution as sources, even though technically they are not, because most people interested in rebuilding E will not care to rebuild these parsers.

    Those that do wish to rebuild these parsers should set MAKE_PARSERS to "true". This will cause the BYacc/Java executable, byaccj, to be rebuilt from sources, and will cause these parsers to be rebuild from their *.y files using byaccj. The BYacc/Java sources seem to have problems compiling on some platforms. If you encounter such problems, and especially if you figure out how to fix it, please let us know.

    If not set, this defaults to not rebuilding byaccj or the parsers, but just using the generated parsers included in the source distribution as sources.

If there are better or more conventional ways to control these building issues, please let us know.
Unless stated otherwise, all text on this page which is either unattributed or by Mark S. Miller is hereby placed in the public domain.
ERights Home download 
Back to: E 0.8.13e Download and Install E 1st child: E 0.8.14b: Installing on Windows On to: E 0.8.15b Download and Install E
Download    FAQ    API    Mail Archive    Donate

report bug (including invalid html)

Golden Key Campaign Blue Ribbon Campaign