February 28, 2021
Hot Topics:

Signing Java with Microsoft's Authenticode

  • By John Viega
  • Send Email »
  • More Articles »

Special HTML tag

When deploying a signed CAB file in an HTML page, a slight variation on the APPLET tag is used. As with all applets, the name of the class that extends java.applet.Applet goes in the CODE attribute. However, instead of putting the name of the CAB file in the ARCHIVE attribute, where JAR files appear, Authenticode signed CAB files are passed using the PARAM tag. As an illustration, the tag to embed the signed applet "MyApplet" stored in myapp.cab into a Web page would look like:

The named parameter "cabbase" is how Internet Explorer finds the CAB file containing the class specified in the CODE attribute.

Using Microsoft's Client Storage API

It is possible to circumvent the need for a certificate for certain operations by using Microsoft's APIs. Here we'll show you how to use their Client Storage API, which will allow you to write up to a megabyte of data onto the hard disk of the machine running the applet, and later retrieve that data.

The Client Storage API comes with various Microsoft products, including Internet Explorer, so if you have IE installed, you can use it without downloading anything. If you use Microsoft's J++ environment, or just their Java compiler, those classes should be automatically available to you. If you use Sun's JDK, you will need to specify where those classes live before you can compile code that uses them. You should look for the Microsoft Java classes on your machine. On a Windows NT box, they will generally live in C:\WINNT\Java\Classes\classes.zip. You can confirm that the archive you found is the right one by opening it in WinZip or a similar product. If you see many com.ms classes, including com.ms.io.clientstorage, you've found the right archive.

To use these classes, you must have the archive in your class search path. Unfortunately, we've found that if you add those classes to your CLASSPATH variable directly, you are likely to find that your compiler no longer works. Fortunately, there's an easy way around the problem. When you compile an applet, specify the path to the zip file in the -classpath option as such:

javac -classpath C:\WINNT\Java

Here's a simple example applet that will write the string "Hello, World!" to disk, and then read in the same string, drawing it to the applet:

import java.applet.*;
import java.awt.*;
import java.io.*;
import com.ms.io.clientstorage.*;
import com.ms.security.*;

public class AuthenticodeHelloWorld extends Applet{

  private String the_greeting;

  public void start(){ 

    // Tell the security system we want to use the client store.
    try {
      // Open scratch space and write into it.
      OutputStream os = ClientStorageManager.openWritable("scratch.txt");
      os.write("Hello, World!".getBytes());
    } catch(IOException ie) {
      the_greeting = "IOError: " + ie.toString();
    } catch (SecurityException se) {
      the_greeting = "denied: " + se.toString();

    // Read in 13 bytes from a scratch file
    byte[] the_bytes = new byte[13];
    try {
      InputStream is = ClientStorageManager.openReadable("scratch.txt");
    } catch(IOException ie) {
      the_greeting = "IOError: " + ie.toString();
    } catch (SecurityException se) {
      the_greeting = "denied2: " + se.getMessage();

    the_greeting = new String(the_bytes);
  public void paint(Graphics g){
    g.drawString(the_greeting, 20, 20);

The above applet makes three calls to Microsoft APIs. The first call is a call to PolicyEngine.assertPermission to tell the security system that the applet needs to use the client store in order to operate as expected. If the applet can be extended permissions to use the client store based on the local security policy but hasn't been extended those permissions yet, the security system will do so when this call is made.

The second Microsoft API call is the call to ClientStorageManager.openWritable. This call gets an OutputStream object through which your applet can write into the scratch space. The final call to a Microsoft API is the call to ClientStorageManager.openReadable, which provides an InputStream object for reading from the scratch space.

The ClientStorage API can't give your applet access to any files that are outside the client store. Nonetheless, the API does offer a large range of file system functionality. For example, you can make directories, list files, and specify if other scratch space users can use your files. We won't cover this API in any more detail here, but full documentation can be found in Microsoft's Java SDK documentation.

Comparing Authenticode to Netscape Object Signing

Microsoft's Authenticode model is somewhat simpler than the Communicator model for the end user. Assuming the user doesn't know anything about zones, lots of stuff runs without asking the user for permission; the user is prompted only to approve code generally when the code requests full access and doesn't already have permission. Less interaction generally means less hassle for the user. You can make more dialog boxes disappear if you check boxes like, "always trust code from this person," and "always trust code from this site," which appear in the window that announces that code is trying to gain permissions. However, spreading trust around so easily just to avoid dialog boxes can have bad consequences.

Authenticode is also simpler for the developer. There's no need for calls to a capabilities library, meaning you can simply request an access level, as opposed to requesting a set of privileges. However, Netscape is capable of finer-grained access control, which allows the applet to secure only the resources it needs to run without a user feeling the need to give a program complete access to the computer before the applet can run.

Another convenience of Authenticode over Object Signing is that the user only gets prompted at most once per applet. Netscape prompts the user whenever new privileges are requested (which is usually during execution). While the Netscape model is more intrusive, it does afford the user a bit more control over what privilege is granted to an applet.


John Viega is a research associate at Reliable Software Technologies, in Sterling, Va. He holds an M.S. in Computer Science from the University of Virginia. He developed and maintains Mailman, the Gnu mailing list manager. His research interests include software assurance, programming languages, and object-oriented systems.

Tom O'Connor is a software engineer in the research division at Reliable Software Technologies. His interests are computer security and object-oriented software development.

Portions of this article will appear as an appendix in the forthcoming book Securing Java: Getting Down to Business with Mobile Code (John Wiley & Sons, 1998), the second edition of McGraw and Felten's book, Java Security: Hostile Applets, Holes, & Antidotes.

Page 2 of 2

This article was originally published on October 29, 1998

Enterprise Development Update

Don't miss an article. Subscribe to our newsletter below.

Thanks for your registration, follow us on our social networks to keep up-to-date