Security Flaws in SUN JDK 1.1.1 and 1.0.2



We have found twenty four flaws in Sun's Java bytecode verifiers in JDK versions 1.1.1 and 1.0.2. The verifier is the piece of software that inspects untrusted, foreign, or potentially malicious code and decides whether it is safe to admit it into a user's computer. Certain flaws in the verifier may allow malicious applets to gain control of a user's computer. Some flaws are currently benign, but they point to a divergence from the Java virtual machine specification that could cause security holes as the software is modified in the future.

This list of flaws is by no means exhaustive. Our testing methodology, combined with our secure verifier, allows us to continually and automatically test for flaws in commercial Java implementations. Our disassembler helps us easily examine the flaws uncovered by automatic testing. There are numerous categories of flaws that this list does not cover. We will be examining those categories in detail as we develop our verifier and overall research platform.

Netscape Navigator Gold 3.01 on Suns and DEC Alphas exhibits all twenty-four of the flaws in JDK 1.0.2 mentioned below. We have sample applets for each flaw that pass Java safety and conformance verification. All but one (Flaw #8, due to its nature, cannot possibly be instantiated) of these fault containing applets are locally instantiated and executed in the user's browser on those two platforms.

The test results indicating problems in JDK 1.1.1 come from running the standalone 1.1.1 verifier in the most secure manner possible, as described to us by Sun. Fifteen of twenty-four flaws exist in JDK 1.1.1. Overall, we are concerned that there are so many different ways to invoke, and therefore test, verification.

The test run that produced these flaws was made on April 23, 1997. The test suite at that time consisted of a few thousand mutated class files that exercised about 75% of the axioms in our verifier.

Sun has posted a clarification regarding their response to our work.

Legend

Security hole
Possible security hole
Weakness/Divergence from the specification
Ambiguity

TYPESAFETY ERRORS

Java security depends on type-safety. Lapses in checking incoming applets for type-safety may allow rogue applets to gain access to private information or to invoke services to which they do not have permission.

1. It is possible to convert any number into a pointer to any object in the JVM, enabling rogue clients to gain access to priviledged information in Java virtual machines or otherwise force the JVM to perform an illegal operation. Java's safety relies on the fact that all accesses are strongly-typed. To guard this, there are numerous safety checks that are performed for each access which make sure that, for instance, a field designated to hold a string object only has strings assigned to it. There is, however, a flaw in one part of the Java virtual machine that enables applets to assign a long or double value into an object reference. This enables an applet to create forged pointers to any information within the system.

We have constructed a sample applet that exploits this flaw and creates forged pointers to private information in a JVM. Javasoft's JDK 1.0.2 on all platforms and Netscape's Navigator Gold 3.01 (and earlier versions) on the Sun and Alpha platforms exhibit this flaw.

2. An exception descriptor in a Java class file may be invalid. An invalid descriptor could crash the JVM, or otherwise force it to perform an illegal operation. This flaw exists in JDK 1.0.2.

3. Thrown exception descriptors may be valid indices into the constant pool, but not of the correct type. An invalid descriptor could crash the JVM, or otherwise force it to perform an illegal operation. This flaw exists in JDK 1.0.2.

4. Typesafety of double and long operands may be compromised. A client can split longs and doubles on the operand stack. JVM needs to maintain the integrity of all data types on the Java operation stack. In particular, JVM should guarantee that long and double operands are not split by bytecode operations. However, in the case of one instruction, this check is not performed. Consequently, it is possible to create free-floating mistyped data on the Java operand stack.

While we have not come up with a way to exploit this hole, we are concerned that the interaction of this flaw with JIT compilation has security ramifications. This flaw exists in JDK 1.0.2 and Netscape Gold 3.01 (and earlier versions) on Suns and Alphas.

5. A method can declare its maximum number of locals (which include space for arguments) to be N, but take M arguments in its signature, where M can be greater than N. A virtual machine compiler or interpreter that relies solely on information mentioned in the maxlocals field could crash or otherwise be violated. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2, and prompted the security patch from Sun.

6. A certain internal length inconsistency in a class file is not caught. An internal length inconsistency may cause the JVM to perform an illegal operation. Reading past the end of a submitted class file enables an applet to probe for information that happened to be stored at that location.

This flaw exists in JDK 1.1.1 and JDK 1.0.2.

ACCESS FLAG CHECKS

Java class methods and fields carry access information with them. Certain combinations of access flags are illegal, and need to be caught by the JVM. Illegal combinations of access flags could lead to safety violations or ambiguous execution.

7. A class may simultaneously be an interface and final. This flaw exists in JDK 1.0.2.

8. A method may simultaneously be Abstract & Final. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

9. A method may simultaneously be Native & Abstract. This flaw exists in the JDK 1.1.1 verifier, though the error is caught at instantiation time. We consider the fact that the verifier does not catch this error a weakness.

10. A method may simultaneously be Protected & Private. This flaw exists in JDK 1.1.1 and JDK 1.0.2.

11. A method may simultaneously be Synchronized & Abstract. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

12. A method may simultaneously be Static & Abstract. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

13. A field may simultaneously be Protected & Private. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

14. A field may simultaneously be Final & Volatile. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

15. Fields in interfaces may not be final. The JVM specification requires that all fields in interfaces be final. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

16. Non-static fields may take a constant attribute. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2. This is no longer in violation of the JVM specification due to an errata released on April 17, 1997. However, the verifiers tested, when released, were in violation of the JVM specification.

17. Access flags for some methods are unrestricted. Certain access methods on sensitive methods may enable clients to break the type-safety of the Java virtual machine. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

INSTRUCTION AND CLASS FILE VALIDITY

Java byte-code instructions need to conform to a standard format defined in the JVM specification. Failure to conform should be caught by the Java verifier. Any code that depends on unchecked assumptions about the bytecode can be made to crash.

18. The verifier does not check a certain instruction in the Java bytecode stream for proper conformance against the JVM specification. A virtual machine that assumed that the instruction stream is valid with regard to the JVM specification could be forced to perform illegal operations. This flaw exists in JDK 1.1.1.

19. The verifier does not check a certain instruction in the Java bytecode stream for proper conformance against the JVM specification. (This instruction is not the same one as described in 18). A virtual machine that assumed that the instruction stream is valid with regard to the JVM specification could be forced to perform illegal operations. This flaw exists in JDK 1.0.2.

20. Certain strings may contain illegal bytes. The JVM specification prohibits these bytes from appearing in such strings. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

21. The ranges of code protected by certain Java constructs can overlap. The JVM definition is ambiguous when it comes to the treatment of such constructs, and this could lead to incompatibilities between different Java versions. While the JVM book explicitly states that overlap is not checked, we believe that the lack of checking will result in incompatible Java clients and applets with unpredictable behaviour. This problem exists in JDK 1.1.1 as well as JDK 1.0.2.

22. The class file may contain unreachable code. While this does not immediately lead to an error, it is a weakness. A JIT compiler may attempt to compile the unreachable bytecode, whose safety is not verified. Assumptions in the compiler that the code is type-safe may be exploited to crash the JVM without executing the unreachable code. This flaw exists in JDK 1.1.1 as well as JDK 1.0.2.

23. The verifier does not catch another internal length inconsistency in an applet. Such inconsistencies, pads and gaps in the class file may be potential locations to attach viruses. This flaw exists in JDK 1.0.2.

24. Class namespace management may be confused by malformed class names. Correct, predictable namespace management is crucial to the safe execution of a JVM. This flaw exists in JDK 1.0.2.

We have example applets for each of these flaws, and some links with which you can compare the output of the Kimera verifier to those of commercial Java virtual machines. However, we are distributing this information only to those with a need to know. Please contact us if you feel you should have access to bytecode samples, verifier output and the disassembly of the class files.


Emin Gün Sirer & Brian Bershad

Project Kimera
Department of Computer Science and Engineering
© 1997, University of Washington