The JavaToaster

Laughing

When Java was unveiled to the world in 1995 it was as a secure web browser language. Java has gone through a long evolutionary process since then that has taken it from applets to the very heart of the corporation. Java’s early history as a programming language for embedded applications is often forgotten. Java’s designers dreamed about a programming language that would become ubiquitous in the converging worlds of digitally controlled consumer devices and computers.

The hardware has finally caught up with the early promise of embedded Java devices. It is now almost as easy to program domestic appliances in Java as it is to run a multi-national corporation using J2EE. In this article we look at the history of Java’s first embedded application - the JavaToaster - and the great foundations laid for us by those early design decisions.

The work on Java began quietly enough with a small team put together by Sun to try to figure out some use for all that hardware. The “Green Team” as it was then known soon reached their ground-breaking conclusion: that digital devices would become ubiquitous and that only an entirely new breed of programming language could exploit this. The new language was initially named “Oak” because of its rigid and inexpressive syntax. At the same time, the team outlined their vision of the JavaToaster to explore the concept of ubiquitous computing.

The man most often credited with inventing Java, James Gosling, realized that to toast bread efficiently required not one, but two CPUs. Placed either side of the bread, the CPUs would heat both sides of the slice at once. However, Gosling’s early work on the JavaToaster program running on consumer-oriented commodity Intel CPUs uncovered a serious problem.

When an Intel CPU has no useful work to do, it triggers a power-saving bug that reduces heat dissipation to less than 1% of its full-workload dissipation - not enough to produce toast. Despite many years of effort, Intel engineers have been unable to correct this fault, which has plagued generations of Intel CPUs. Intel executives have been forced to issue repeated denials that this is even a bug - claiming it to be a feature of the CPU.

This limitation is the same one that has afflicted PCs running Microsoft’s Windows operating systems for many years, forcing Microsoft to work around the power-saving bug by introducing a routine that performs useless calculations whenever the CPU is in danger of having nothing to do. In this way, Microsoft engineers were able to allow the PC to continue to produce heat without user intervention.

Gosling saw that simply using two CPUs was not enough. The Java program that controlled the toaster would only be able to run on one CPU at a time. The toaster could brown first one side of bread and then the other, but not both simultaneously. Unable to use Microsoft’s patent-protected endless loop technology to keep both CPUs hot (Sun’s lawyers had earlier been unable to strike a licensing deal with Redmond) and facing the failure of the entire project, Gosling was forced to rethink the problem while the rest of the team tried to look busy.

He began by trying to divide the Java processing between the two CPUs, but was frustrated to find each CPU spending half its time power-saving, yielding only 50% of its full heat output. The toaster ran slower than ever, often just drying the bread out rather than toasting it.

A crucial meeting in Monterey early in 1995 between John Gage, director of Sun’s Science Office and top executives from the domestic appliance industry seemed to sound Java’s death knell when it was pointed out that there was no market for server-grade bread-driers, even if Java’s advanced security features made it safe for consumers to log in to the JavaToaster’s browser-based interface and dry bread from the other side of the world.

In despair, Gosling and the other less famous but equally important members of the team cut communication with Sun and locked themselves in their office in Menlo Park to find the solution. The team spent 18 months working around the clock to produce what we now know as Java’s thread implementation.

Originally invented by the National Security Agency as a way of covertly introducing untraceable programming errors, today threads are so commonplace that we forget what a revelation this new technology was. For the first time, threads made it possible to execute simple programs in complicated ways that used lots of processors. For the Java team it was a breakthrough. They were finally able to run Java programs that used both processors simultaneously.

The vision that took Gosling and the Green Team through those dark early years has not been in vain; Java can now be found in all manner of devices where it wasn’t previously found to be necessary, such as PDAs, mobile telephones and webservers.

The Java team’s vision was so far ahead of its time that, 9 years later, the hardware is only just beginning to catch up with the early promise of domestic appliances. In 1995, and with 20 years of research behind them, Intel had only been able to increase the heat output of their processors to around 10 Watts.

However, recent advances in Intel’s fabrication process have enabled them to push up the heat output of their processors substantially (to over 100W for the Pentium-4 3GHz). Coupled with a huge increase in heatsink size which helps to spread the processor’s heat output over a whole slice of bread, and the JavaToaster vision stands on the threshold of becoming a reality.

Today, it is possible to make a JavaToaster of your own using off-the-shelf components with little more than a PhD, a team of engineers and a budget of several million dollars. Gosling’s work on designing the ultimate appliance-centric programming language has turned toaster design into little more than a hardware problem.

Code listing: part of the JavaToaster2.2 appliance source code, updated to take advantage of the latest J2EE specifications.

package javax.appliance.toaster;

import java.util.*;
import javax.ejb.*;
import javax.corba.*;
import javax.jndi.*;
import javax.servlet.*;
import javax.servlet.http.*;

public class Toaster extends HttpServlet {

    private BrownnessKnobEJB _brownnessKnob;

    public void init() {
        InitialContext namingContext = new InitialContext();
        Object brownnessKnobEJBHomeObject = namingContext.lookup("ejb/brownnessKnob");
        BrownnessKnobEJBHome brownnessKnobEJBHome = (BrownnessKnobEJBHome) 
            PortableRemoteObject.narrow(brownnessKnobEJBHomeObject);

        BrownnessKnobEJBPrimaryKey knobPrimaryKey =
            new BrownnessKnobEJBPrimaryKey("theknob");
        _brownnessKnob = BrownnessKnobEJBHome.findByPrimaryKey(knobPrimaryKey);
    }

    public void doGet(HttpServletRequest request, HttpServletResponse response) 
        throws IOException, ServletException
    {
        PrintWriter out = response.getWriter();
        response.setContentType("text/plain");

        if (request.getHeader("User-Agent").indexOf("Internet Explorer") == -1)
            out.println("This toaster has been optimized to work with Microsoft "
                        + "Internet Explorer. Please downgrade your browser.");

        else if (! request.getParameter("command").equals("MakeToast"))
            out.println("Error: This toaster is not configured to perform the "
                        + "requested operation. If you feel this is an error, "
                        + "please inform the toaster's administrator.");

        else if (! request.getParameter("password").equals("Gosling"))
            out.println("Error: You are not authorized to make toast using this "
                        + "toaster. Your access attempt has been logged and may "
                        + "be reported to law enforcement officials.");

        else {
            out.println("Please wait while the toaster makes toast.");
            out.flush();

            try {
                int brownness = _brownnessButton.getBrownness();
                makeToast(brownness);

                out.println("Your toast is now ready. Please remove your toast "
                            + "from the toaster before eating it. "
                            + "Caution: toast is made from hot bread "
                            + "- risk of scalding!");

                out.println("The manufacturer offers NO WARRANTY for your toaster's "
                            + "fitness for a particular purpose, including the "
                            + "implied purpose of being fit for making toast, "
                            + "unless laws in your jurisdiction make it illegal for "
                            + "us to say this.");

            } catch (RemoteException ex) {

                out.println("Network connection to brownness knob appears to "
                            + "be down. Please retry your toasting request. "
                            + "If this problem persists, please contact the "
                            + "toaster's administrator.");
            }   
        }
    }

    private void makeToast(final int brownness) {
        Thread frontToastingThread = new Thread() {
            public void run() {
                double d = 1.6e17;
                for (int i=0; i