Merge
authorchegar
Fri, 10 Jan 2014 15:04:46 +0000
changeset 22342 c83795c442b7
parent 22256 191b8793a532 (current diff)
parent 22341 4689530d03b9 (diff)
child 22343 0f59fce296a3
Merge
jdk/make/CreateJars.gmk
jdk/make/CreateSecurityJars.gmk
jdk/make/Images.gmk
jdk/src/share/classes/java/lang/SecurityManager.java
jdk/src/share/classes/java/util/jar/JarFile.java
jdk/src/share/classes/java/util/jar/JarVerifier.java
jdk/src/share/classes/java/util/logging/LogManager.java
jdk/src/share/classes/javax/security/auth/login/LoginContext.java
jdk/src/share/classes/sun/security/util/SecurityConstants.java
--- a/jdk/make/CompileJavaClasses.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/CompileJavaClasses.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -274,11 +274,6 @@
       $(JDK_TOPDIR)/src/solaris/classes/sun/nio/ch/sctp/SctpMultiChannelImpl.java \
       $(JDK_TOPDIR)/src/solaris/classes/sun/nio/ch/sctp/SctpServerChannelImpl.java
 
-  # JObjC.jar contains 1.5 byte-code...so skip it here :-(
-  # MACOSX_SRC_DIRS += $(JDK_TOPDIR)/src/macosx/native/jobjc/src
-  # EXCLUDES += tests/java/com/apple/jobjc
-
-  EXCLUDES += com/apple/jobjc
 endif
 
 # The security classes should not end up in the classes directory as that will prevent them
@@ -354,44 +349,6 @@
 
 ##########################################################################################
 
-ifeq ($(OPENJDK_TARGET_OS), macosx)
-  #
-  # JObjC.jar is compiled with BOOT_JAVAC which (may) not support the "-h" flag.
-  # so we first compile classes with BOOT_JAVAC and then with JDK_JAVAC :-(
-  #
-  $(eval $(call SetupJavaCompiler,GENERATE_15BYTECODE, \
-      JAVAC := $(JAVAC), \
-      FLAGS := -source 1.5 -target 1.5 -g -bootclasspath $(BOOT_RTJAR) -cp $(JDK_OUTPUTDIR)/../langtools/dist/lib/classes.jar $(DISABLE_WARNINGS), \
-      SERVER_DIR := $(SJAVAC_SERVER_DIR), \
-      SERVER_JVM := $(SJAVAC_SERVER_JAVA)))
-
-  $(eval $(call SetupJavaCompilation,BUILD_JOBJC, \
-      SETUP := GENERATE_15BYTECODE, \
-      DISABLE_SJAVAC := true, \
-      SRC := $(JDK_TOPDIR)/src/macosx/native/jobjc/src/core/java \
-          $(JDK_TOPDIR)/src/macosx/native/jobjc/src/runtime-additions/java \
-          $(JDK_OUTPUTDIR)/gensrc_jobjc/src, \
-      INCLUDES := com/apple/jobjc, \
-      EXCLUDES := tests/java/com/apple/jobjc, \
-      BIN := $(JDK_OUTPUTDIR)/jobjc_classes, \
-      JAR := $(JDK_OUTPUTDIR)/lib/JObjC.jar, \
-      JARINDEX := true))
-
-  $(BUILD_JOBJC): $(BUILD_JDK)
-
-  $(eval $(call SetupJavaCompilation,BUILD_JOBJC_HEADERS, \
-      SETUP := GENERATE_JDKBYTECODE, \
-      SRC := $(JDK_TOPDIR)/src/macosx/native/jobjc/src/core/java \
-          $(JDK_TOPDIR)/src/macosx/native/jobjc/src/runtime-additions/java \
-          $(JDK_OUTPUTDIR)/gensrc_jobjc/src, \
-      INCLUDES := com/apple/jobjc, \
-      EXCLUDES := tests/java/com/apple/jobjc, \
-      BIN := $(JDK_OUTPUTDIR)/jobjc_classes_headers, \
-      HEADERS := $(JDK_OUTPUTDIR)/gensrc_headers_jobjc))
-
-$(BUILD_JOBJC_HEADERS): $(BUILD_JDK)
-
-endif
 
 ##########################################################################################
 
--- a/jdk/make/CreateJars.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/CreateJars.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -668,13 +668,6 @@
 
 ##########################################################################################
 
-ifeq ($(OPENJDK_TARGET_OS), macosx)
-  $(eval $(call SetupArchive,BUILD_JOBJC_JAR, , \
-      SRCS := $(JDK_OUTPUTDIR)/jobjc_classes, \
-      JAR := $(IMAGES_OUTPUTDIR)/lib/JObjC.jar, \
-      JARINDEX := true))
-endif
-
 # This file is imported from hotspot in Import.gmk. Copying it into images/lib so that
 # all jars can be found in one place when creating images in Images.gmk. It needs to be
 # done here so that clean targets can be simple and accurate.
--- a/jdk/make/GenerateSources.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/GenerateSources.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -85,11 +85,6 @@
 include gensrc/GensrcSwing.gmk
 GENSRC += $(GENSRC_SWING_BEANINFO) $(GENSRC_SWING_NIMBUS)
 
-ifeq ($(OPENJDK_TARGET_OS), macosx)
-  include gensrc/GensrcJObjC.gmk
-  GENSRC += $(GENSRC_JOBJC)
-endif
-
 $(GENSRC): $(BUILD_TOOLS)
 
 all: $(GENSRC)
--- a/jdk/make/Images.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/Images.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -283,14 +283,13 @@
 	$(ECHO) $(LOG_INFO) Creating $(patsubst $(OUTPUT_ROOT)/%,%,$@)
 	$(MKDIR) -p $@
 
-# In the old build, JObjC.jar is not part of the meta-index
 $(JRE_IMAGE_DIR)/lib/meta-index: $(JRE_LIB_TARGETS)
 	$(ECHO) $(LOG_INFO) Generating $(patsubst $(OUTPUT_ROOT)/%,%,$@)
-	$(CD) $(@D) && $(TOOL_BUILDMETAINDEX) -o meta-index `$(LS) *.jar | $(SED) 's/JObjC\.jar//g'`
+	$(CD) $(@D) && $(TOOL_BUILDMETAINDEX) -o meta-index *.jar
 
 $(JDK_IMAGE_DIR)/jre/lib/meta-index: $(JDKJRE_LIB_TARGETS)
 	$(ECHO) $(LOG_INFO) Generating $(patsubst $(OUTPUT_ROOT)/%,%,$@)
-	$(CD) $(@D) && $(TOOL_BUILDMETAINDEX) -o meta-index `$(LS) *.jar | $(SED) 's/JObjC\.jar//g'`
+	$(CD) $(@D) && $(TOOL_BUILDMETAINDEX) -o meta-index *.jar
 
 $(JRE_IMAGE_DIR)/lib/ext/meta-index: $(JRE_LIB_TARGETS)
 	$(ECHO) $(LOG_INFO) Generating $(patsubst $(OUTPUT_ROOT)/%,%,$@)
--- a/jdk/make/Profiles.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/Profiles.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -105,10 +105,6 @@
   ALL_JARS += $(IMAGES_OUTPUTDIR)/lib/ext/sunmscapi.jar
 endif
 
-ifeq ($(OPENJDK_TARGET_OS), macosx)
-  ALL_JARS += $(IMAGES_OUTPUTDIR)/lib/JObjC.jar
-endif
-
 ifeq ($(PROFILE), profile_1)
   PROFILE_JARS := $(PROFILE_1_JARS)
 else ifeq ($(PROFILE), profile_2)
--- a/jdk/make/lib/NetworkingLibraries.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/lib/NetworkingLibraries.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -25,6 +25,7 @@
 
 LIBNET_SRC_DIRS := $(JDK_TOPDIR)/src/share/native/java/net \
     $(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/native/java/net \
+    $(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/native/sun/net/ \
     $(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/native/sun/net/dns \
     $(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/native/sun/net/spi
 
--- a/jdk/make/lib/PlatformLibraries.gmk	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/lib/PlatformLibraries.gmk	Fri Jan 10 15:04:46 2014 +0000
@@ -136,64 +136,6 @@
 
 ##########################################################################################
 
-ifeq ($(OPENJDK_TARGET_OS), macosx)
-
-  $(eval $(call SetupNativeCompilation,BUILD_LIBJOBJC32, \
-      LIBRARY := JObjC, \
-      OUTPUT_DIR := $(JDK_OUTPUTDIR)/objs/libjobjc32, \
-      SRC := $(JDK_TOPDIR)/src/macosx/native/jobjc/src/core/native \
-          $(JDK_TOPDIR)/src/macosx/native/jobjc/src/runtime-additions/native, \
-      LANG := C, \
-      OPTIMIZATION := LOW, \
-      CFLAGS := -fpascal-strings \
-          -fobjc-gc \
-          -gdwarf-2 \
-          $(CFLAGS_JDKLIB) -I$(JDK_OUTPUTDIR)/gensrc_headers_jobjc \
-          -F/System/Library/Frameworks/JavaVM.framework/Frameworks \
-          -m32, \
-      LDFLAGS := $(LDFLAGS_JDKLIB) \
-          -m32, \
-      LDFLAGS_SUFFIX := -framework Foundation -framework JavaVM \
-          -F/System/Library/Frameworks/JavaVM.framework/Frameworks \
-          -framework JavaNativeFoundation \
-          -lffi, \
-      OBJECT_DIR := $(JDK_OUTPUTDIR)/objs/libjobjc32, \
-      DEBUG_SYMBOLS := $(DEBUG_ALL_BINARIES)))
-
-  $(eval $(call SetupNativeCompilation,BUILD_LIBJOBJC64, \
-      LIBRARY := JObjC, \
-      OUTPUT_DIR := $(JDK_OUTPUTDIR)/objs/libjobjc64, \
-      SRC := $(JDK_TOPDIR)/src/macosx/native/jobjc/src/core/native \
-          $(JDK_TOPDIR)/src/macosx/native/jobjc/src/runtime-additions/native, \
-      LANG := C, \
-      OPTIMIZATION := LOW, \
-      CFLAGS := -fpascal-strings \
-          -fobjc-gc \
-          -gdwarf-2 \
-          $(CFLAGS_JDKLIB) -I$(JDK_OUTPUTDIR)/gensrc_headers_jobjc \
-          -F/System/Library/Frameworks/JavaVM.framework/Frameworks \
-          , \
-      LDFLAGS := -fpascal-strings \
-          -fobjc-gc \
-          -gdwarf-2 \
-          $(LDFLAGS_JDKLIB) \
-          $(call SET_SHARED_LIBRARY_ORIGIN), \
-      LDFLAGS_SUFFIX := -framework Foundation -framework JavaVM \
-          -F/System/Library/Frameworks/JavaVM.framework/Frameworks \
-          -framework JavaNativeFoundation \
-          -lffi, \
-      OBJECT_DIR := $(JDK_OUTPUTDIR)/objs/libjobjc64, \
-      DEBUG_SYMBOLS := $(DEBUG_ALL_BINARIES)))
-
-  $(INSTALL_LIBRARIES_HERE)/$(LIBRARY_PREFIX)JObjC$(SHARED_LIBRARY_SUFFIX): $(BUILD_LIBJOBJC32) $(BUILD_LIBJOBJC64)
-	$(LIPO) -create -output $@ $(BUILD_LIBJOBJC32) $(BUILD_LIBJOBJC64)
-
-  BUILD_LIBRARIES += $(INSTALL_LIBRARIES_HERE)/$(LIBRARY_PREFIX)JObjC$(SHARED_LIBRARY_SUFFIX)
-
-endif
-
-##########################################################################################
-
 ifndef OPENJDK
   ifeq ($(OPENJDK_TARGET_OS), windows)
 
--- a/jdk/make/mapfiles/libnet/mapfile-vers	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/make/mapfiles/libnet/mapfile-vers	Fri Jan 10 15:04:46 2014 +0000
@@ -86,6 +86,8 @@
 		Java_java_net_PlainSocketImpl_socketConnect;
 		Java_java_net_PlainDatagramSocketImpl_getTimeToLive;
 		Java_java_net_PlainDatagramSocketImpl_setTimeToLive;
+		Java_sun_net_PortConfig_getUpper0;
+		Java_sun_net_PortConfig_getLower0;
 		Java_sun_net_dns_ResolverConfigurationImpl_localDomain0;
 		Java_sun_net_dns_ResolverConfigurationImpl_fallbackDomain0;
 		Java_sun_net_sdp_SdpSupport_convert0;
--- a/jdk/src/macosx/native/sun/awt/splashscreen/splashscreen_sys.m	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/macosx/native/sun/awt/splashscreen/splashscreen_sys.m	Fri Jan 10 15:04:46 2014 +0000
@@ -290,8 +290,8 @@
         SplashUnlock(splash);
         rc = poll(pfd, 1, timeout);
         SplashLock(splash);
-        if (splash->isVisible>0 && SplashTime() >= splash->time +
-                splash->frames[splash->currentFrame].delay) {
+        if (splash->isVisible > 0 && splash->currentFrame >= 0 &&
+                SplashTime() >= splash->time + splash->frames[splash->currentFrame].delay) {
             SplashNextFrame(splash);
             SplashRedrawWindow(splash);
         }
--- a/jdk/src/share/classes/com/sun/beans/decoder/DocumentHandler.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/beans/decoder/DocumentHandler.java	Fri Jan 10 15:04:46 2014 +0000
@@ -29,6 +29,7 @@
 import java.beans.ExceptionListener;
 
 import java.io.IOException;
+import java.io.StringReader;
 
 import java.lang.ref.Reference;
 import java.lang.ref.WeakReference;
@@ -246,6 +247,14 @@
     }
 
     /**
+     * Disables any external entities.
+     */
+    @Override
+    public InputSource resolveEntity(String publicId, String systemId) {
+        return new InputSource(new StringReader(""));
+    }
+
+    /**
      * Prepares this handler to read objects from XML document.
      */
     @Override
--- a/jdk/src/share/classes/com/sun/crypto/provider/TlsRsaPremasterSecretGenerator.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/crypto/provider/TlsRsaPremasterSecretGenerator.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -72,13 +72,17 @@
             throw new IllegalStateException(
                 "TlsRsaPremasterSecretGenerator must be initialized");
         }
-        if (random == null) {
-            random = new SecureRandom();
+        byte[] b = spec.getEncodedSecret();
+        if (b == null) {
+            if (random == null) {
+                random = new SecureRandom();
+            }
+            b = new byte[48];
+            random.nextBytes(b);
+            b[0] = (byte)spec.getMajorVersion();
+            b[1] = (byte)spec.getMinorVersion();
         }
-        byte[] b = new byte[48];
-        random.nextBytes(b);
-        b[0] = (byte)spec.getMajorVersion();
-        b[1] = (byte)spec.getMinorVersion();
+
         return new SecretKeySpec(b, "TlsRsaPremasterSecret");
     }
 
--- a/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibEntry.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibEntry.java	Fri Jan 10 15:04:46 2014 +0000
@@ -27,17 +27,9 @@
 
 // java imports
 //
+import com.sun.jmx.snmp.SnmpDefinitions;
 import java.io.Serializable;
-import java.util.Hashtable;
-import java.util.Enumeration;
-
-// jmx imports
-//
-import com.sun.jmx.snmp.SnmpValue;
-import com.sun.jmx.snmp.SnmpVarBind;
 import com.sun.jmx.snmp.SnmpStatusException;
-import com.sun.jmx.snmp.agent.SnmpMibOid;
-import com.sun.jmx.snmp.agent.SnmpMibNode;
 
 /**
  * Represents a node in an SNMP MIB which corresponds to a table entry
@@ -99,7 +91,9 @@
      */
     public void validateVarId(long arc, Object userData)
         throws SnmpStatusException {
-        if (isVariable(arc) == false) throw noSuchNameException;
+        if (isVariable(arc) == false) {
+            throw new SnmpStatusException(SnmpDefinitions.snmpRspNoSuchName);
+        }
     }
 
     /**
--- a/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibGroup.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibGroup.java	Fri Jan 10 15:04:46 2014 +0000
@@ -108,8 +108,9 @@
      */
     public void validateVarId(long arc, Object userData)
         throws SnmpStatusException {
-        if (isVariable(arc) == false)
-            throw noSuchObjectException;
+        if (isVariable(arc) == false) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
     }
 
 
@@ -360,17 +361,20 @@
             validateVarId(arc, data);
 
             // The trailing .0 is missing in the OID
-            if (depth+2 > length)
-                throw noSuchInstanceException;
+            if (depth+2 > length) {
+                throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+            }
 
             // There are too many arcs left in the OID (there should remain
             // a single trailing .0)
-            if (depth+2 < length)
-                throw noSuchInstanceException;
+            if (depth+2 < length) {
+                throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+            }
 
             // The last trailing arc is not .0
-            if (oid[depth+1] != 0L)
-                throw noSuchInstanceException;
+            if (oid[depth+1] != 0L) {
+                throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+            }
 
             // It's one of our variable, register this node.
             handlers.add(this,depth,varbind);
@@ -389,12 +393,13 @@
         int length = oid.length;
         SnmpMibNode node = null;
 
-        if (handlers == null)
+        if (handlers == null) {
             // This should be considered as a genErr, but we do not want to
             // abort the whole request, so we're going to throw
             // a noSuchObject...
             //
-            throw noSuchObjectException;
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
         final Object data = handlers.getUserData();
         final int pduVersion = handlers.getRequestPduVersion();
@@ -430,7 +435,7 @@
                                                         depth+1,handlers,
                                                         checker);
                 }catch(SnmpStatusException ex) {
-                    throw noSuchObjectException;
+                    throw new SnmpStatusException(SnmpStatusException.noSuchObject);
                 } finally {
                     checker.remove(depth);
                 }
@@ -455,7 +460,7 @@
                     try {
                         checker.checkCurrentOid();
                     } catch(SnmpStatusException e) {
-                        throw noSuchObjectException;
+                        throw new SnmpStatusException(SnmpStatusException.noSuchObject);
                     } finally {
                         checker.remove(depth,2);
                     }
@@ -500,7 +505,7 @@
             // The oid is not valid, we will throw an exception in order
             // to try with the next valid identifier...
             //
-            throw noSuchObjectException;
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
 
         } catch (SnmpStatusException e) {
             // We didn't find anything at the given arc, so we're going
--- a/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibNode.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibNode.java	Fri Jan 10 15:04:46 2014 +0000
@@ -155,7 +155,7 @@
                           long[] oid, int depth,
                           SnmpRequestTree handlers)
         throws SnmpStatusException {
-        throw noSuchObjectException;
+        throw new SnmpStatusException(SnmpStatusException.noSuchObject);
     }
 
     /**
@@ -183,7 +183,7 @@
                                  long[] oid, int pos, int depth,
                                  SnmpRequestTree handlers, AcmChecker checker)
         throws SnmpStatusException {
-        throw noSuchObjectException;
+        throw new SnmpStatusException(SnmpStatusException.noSuchObject);
     }
 
     /**
@@ -346,8 +346,9 @@
         final int[] a = table;
         final int val= (int) value;
 
-        if (a == null)
-            throw noSuchObjectException;
+        if (a == null) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
         int low= 0;
         int max= a.length;
@@ -356,11 +357,13 @@
 
         // Basic check
         //
-        if (max < 1)
-            throw noSuchObjectException;
+        if (max < 1) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
-        if (a[max-1] <= val)
-            throw noSuchObjectException;
+        if (a[max-1] <= val) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
         while (low <= max) {
             elmt= a[curr];
@@ -400,15 +403,4 @@
      * Contains the list of variable identifiers.
      */
     protected int[] varList;
-
-    /**
-     * Contains a predefined exception that is often fired when an
-     * object is not found in the MIB.
-     */
-    static final protected SnmpStatusException noSuchInstanceException =
-        new SnmpStatusException(SnmpStatusException.noSuchInstance);
-    static final protected SnmpStatusException noSuchObjectException =
-        new SnmpStatusException(SnmpStatusException.noSuchObject);
-    static final protected SnmpStatusException noSuchNameException =
-        new SnmpStatusException(SnmpDefinitions.snmpRspNoSuchName);
 }
--- a/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibOid.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibOid.java	Fri Jan 10 15:04:46 2014 +0000
@@ -160,12 +160,10 @@
 
         if (depth > length) {
             // Nothing is left... the oid is not valid
-            throw noSuchObjectException;
-
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
         } else if (depth == length) {
             // The oid is not complete...
-            throw noSuchInstanceException;
-
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
         } else {
             // Some children variable or subobject is being querried
             // getChild() will raise an exception if no child is found.
@@ -205,12 +203,13 @@
         final int length = oid.length;
         SnmpMibNode node = null;
         long[] result = null;
-        if (handlers == null)
+        if (handlers == null) {
             // This should be considered as a genErr, but we do not want to
             // abort the whole request, so we're going to throw
             // a noSuchObject...
             //
-            throw noSuchObjectException;
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
         final Object data = handlers.getUserData();
         final int pduVersion = handlers.getRequestPduVersion();
@@ -235,7 +234,7 @@
                 // SnmpOid result = null;
                 if (child == null) {
                     // shouldn't happen
-                    throw noSuchObjectException;
+                    throw new SnmpStatusException(SnmpStatusException.noSuchObject);
                     // validateVarId(index);
                     // handlers.add(this,varbind,depth);
                     // result = new SnmpOid(0);
@@ -444,11 +443,13 @@
         // first we need to retrieve the identifier in the list of children
         //
         final int pos= getInsertAt(id);
-        if (pos >= nbChildren)
-            throw noSuchObjectException;
+        if (pos >= nbChildren) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
-        if (varList[pos] != (int) id)
-            throw noSuchObjectException;
+        if (varList[pos] != (int) id) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
 
         // Access the node
         //
@@ -456,10 +457,11 @@
         try {
             child = children.elementAtNonSync(pos);
         } catch(ArrayIndexOutOfBoundsException e) {
-            throw noSuchObjectException;
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
         }
-        if (child == null)
-            throw noSuchInstanceException;
+        if (child == null) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+        }
         return child;
     }
 
--- a/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibTable.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/jmx/snmp/agent/SnmpMibTable.java	Fri Jan 10 15:04:46 2014 +0000
@@ -280,7 +280,7 @@
             SnmpVarBind var;
             for (Enumeration<SnmpVarBind> e= r.getElements(); e.hasMoreElements();) {
                 var = e.nextElement();
-                r.registerGetException(var,noSuchInstanceException);
+                r.registerGetException(var,new SnmpStatusException(SnmpStatusException.noSuchInstance));
             }
         }
 
@@ -1607,8 +1607,9 @@
     protected SnmpOid getNextOid(SnmpOid oid, Object userData)
         throws SnmpStatusException {
 
-        if (size == 0)
-            throw noSuchInstanceException;
+        if (size == 0) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+        }
 
         final SnmpOid resOid = oid;
 
@@ -1619,7 +1620,7 @@
         if (last.equals(resOid)) {
             // Last element of the table ...
             //
-            throw noSuchInstanceException;
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
         }
 
         // First find the oid. This will allow to speed up retrieval process
@@ -1641,12 +1642,12 @@
                 // XX last = (SnmpOid) oids.elementAt(newPos);
                 last = tableoids[newPos];
             } catch(ArrayIndexOutOfBoundsException e) {
-                throw noSuchInstanceException;
+                throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
             }
         } else {
             // We are dealing with the last element of the table ..
             //
-            throw noSuchInstanceException;
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
         }
 
 
@@ -1668,8 +1669,9 @@
      */
     protected SnmpOid getNextOid(Object userData)
         throws SnmpStatusException {
-        if (size == 0)
-            throw noSuchInstanceException;
+        if (size == 0) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+        }
         // XX return (SnmpOid) oids.firstElement();
         return tableoids[0];
     }
@@ -1875,10 +1877,10 @@
         // not support creation.
         // We know that the entry does not exists if (isentry == false).
         if (!hasEntry) {
-            if (!handlers.isCreationAllowed())
+            if (!handlers.isCreationAllowed()) {
                 // we're not doing a set
-                throw noSuchInstanceException;
-            else if (!isCreationEnabled())
+                throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+            } else if (!isCreationEnabled())
                 // we're doing a set but creation is disabled.
                 throw new
                     SnmpStatusException(SnmpStatusException.snmpRspNoAccess);
@@ -1922,12 +1924,13 @@
 
             int length = oid.length;
 
-            if (handlers == null)
-            // This should be considered as a genErr, but we do not want to
-            // abort the whole request, so we're going to throw
-            // a noSuchObject...
-            //
-            throw noSuchObjectException;
+            if (handlers == null) {
+                // This should be considered as a genErr, but we do not want to
+                // abort the whole request, so we're going to throw
+                // a noSuchObject...
+                //
+                throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+            }
 
             final Object data = handlers.getUserData();
             final int pduVersion = handlers.getRequestPduVersion();
@@ -1961,7 +1964,7 @@
                 // so we won't find the next element in this table... (any
                 // element in this table will have a smaller OID)
                 //
-                throw noSuchObjectException;
+                throw new SnmpStatusException(SnmpStatusException.noSuchObject);
             } else if (oid[pos] < nodeId) {
                 // we must return the first leaf under the first columnar
                 // object, so we are back to our first case where pos was
@@ -2051,8 +2054,9 @@
                     //     in tables can't be properly supported (all rows
                     //     must have the same holes)
                     //
-                    if (skipEntryVariable(entryoid,var,data,pduVersion))
-                        throw noSuchObjectException;
+                    if (skipEntryVariable(entryoid,var,data,pduVersion)) {
+                        throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+                    }
                 } catch(SnmpStatusException se) {
                     entryoid = getNextOid(data);
                     var = getNextVarEntryId(entryoid,var,data,pduVersion);
@@ -2085,8 +2089,9 @@
             // So we throw the exception.
             // => will skip to next node in the MIB tree.
             //
-            if (entryoid == null || var == -1 ) throw noSuchObjectException;
-
+            if (entryoid == null || var == -1 ) {
+                throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+            }
 
             // So here we know both the row (entryoid) and the column (var)
             //
@@ -2097,8 +2102,9 @@
                 // for this specific entry, it is not readable for any
                 // other entry => skip to next column.
                 //
-                if (!isReadableEntryId(entryoid,var,data))
-                    throw noSuchObjectException;
+                if (!isReadableEntryId(entryoid,var,data)) {
+                    throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+                }
 
                 // Prepare the result and the ACM checker.
                 //
@@ -2161,8 +2167,9 @@
             // No need to continue, we throw an exception.
             // => will skip to next node in the MIB tree.
             //
-            if (entryoid == null || var == -1 )
-                throw noSuchObjectException;
+            if (entryoid == null || var == -1 ) {
+                throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+            }
         }
     }
 
@@ -2182,14 +2189,15 @@
 
         // Control the length of the oid
         //
-        if (pos +2 >= length)
-            throw noSuchInstanceException;
+        if (pos +2 >= length) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchInstance);
+        }
 
         // Check that the entry identifier is specified
         //
-        if (oid[pos] != nodeId)
-            throw noSuchObjectException;
-
+        if (oid[pos] != nodeId) {
+            throw new SnmpStatusException(SnmpStatusException.noSuchObject);
+        }
     }
 
     // ----------------------------------------------------------------------
--- a/jdk/src/share/classes/com/sun/jmx/snmp/daemon/SnmpRequestHandler.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/jmx/snmp/daemon/SnmpRequestHandler.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1146,7 +1146,4 @@
 
     static final private String InterruptSysCallMsg =
         "Interrupted system call";
-
-    static final private SnmpStatusException noSuchNameException =
-        new SnmpStatusException(SnmpDefinitions.snmpRspNoSuchName) ;
 }
--- a/jdk/src/share/classes/com/sun/naming/internal/FactoryEnumeration.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/naming/internal/FactoryEnumeration.java	Fri Jan 10 15:04:46 2014 +0000
@@ -56,9 +56,12 @@
      * references so as not to prevent GC of the class loader.  Each
      * weak reference is tagged with the factory's class name so the
      * class can be reloaded if the reference is cleared.
-
+     *
      * @param factories A non-null list
      * @param loader    The class loader of the list's contents
+     *
+     * This internal method is used with Thread Context Class Loader (TCCL),
+     * please don't expose this method as public.
      */
     FactoryEnumeration(List<NamedWeakReference<Object>> factories,
                        ClassLoader loader) {
@@ -79,7 +82,8 @@
 
             try {
                 if (answer == null) {   // reload class if weak ref cleared
-                    answer = Class.forName(className, true, loader);
+                    Class<?> cls = Class.forName(className, true, loader);
+                    answer = cls;
                 }
                 // Instantiate Class to get factory
                 answer = ((Class) answer).newInstance();
--- a/jdk/src/share/classes/com/sun/naming/internal/VersionHelper12.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/naming/internal/VersionHelper12.java	Fri Jan 10 15:04:46 2014 +0000
@@ -53,21 +53,24 @@
 
 final class VersionHelper12 extends VersionHelper {
 
-    private boolean getSystemPropsFailed = false;
-
-    VersionHelper12() {} // Disallow external from creating one of these.
+    // Disallow external from creating one of these.
+    VersionHelper12() {
+    }
 
     public Class<?> loadClass(String className) throws ClassNotFoundException {
-        ClassLoader cl = getContextClassLoader();
-        return Class.forName(className, true, cl);
+        return loadClass(className, getContextClassLoader());
     }
 
     /**
-      * Package private.
-      */
+     * Package private.
+     *
+     * This internal method is used with Thread Context Class Loader (TCCL),
+     * please don't expose this method as public.
+     */
     Class<?> loadClass(String className, ClassLoader cl)
         throws ClassNotFoundException {
-        return Class.forName(className, true, cl);
+        Class<?> cls = Class.forName(className, true, cl);
+        return cls;
     }
 
     /**
@@ -75,13 +78,13 @@
      * @param codebase A non-null, space-separated list of URL strings.
      */
     public Class<?> loadClass(String className, String codebase)
-        throws ClassNotFoundException, MalformedURLException {
-        ClassLoader cl;
+            throws ClassNotFoundException, MalformedURLException {
 
         ClassLoader parent = getContextClassLoader();
-        cl = URLClassLoader.newInstance(getUrlArray(codebase), parent);
+        ClassLoader cl =
+                 URLClassLoader.newInstance(getUrlArray(codebase), parent);
 
-        return Class.forName(className, true, cl);
+        return loadClass(className, cl);
     }
 
     String getJndiProperty(final int i) {
@@ -99,16 +102,12 @@
     }
 
     String[] getJndiProperties() {
-        if (getSystemPropsFailed) {
-            return null;        // after one failure, don't bother trying again
-        }
         Properties sysProps = AccessController.doPrivileged(
             new PrivilegedAction<Properties>() {
                 public Properties run() {
                     try {
                         return System.getProperties();
                     } catch (SecurityException e) {
-                        getSystemPropsFailed = true;
                         return null;
                     }
                 }
@@ -173,17 +172,32 @@
         return new InputStreamEnumeration(urls);
     }
 
+    /**
+     * Package private.
+     *
+     * This internal method returns Thread Context Class Loader (TCCL),
+     * if null, returns the system Class Loader.
+     *
+     * Please don't expose this method as public.
+     */
     ClassLoader getContextClassLoader() {
+
         return AccessController.doPrivileged(
             new PrivilegedAction<ClassLoader>() {
                 public ClassLoader run() {
-                    return Thread.currentThread().getContextClassLoader();
+                    ClassLoader loader =
+                            Thread.currentThread().getContextClassLoader();
+                    if (loader == null) {
+                        // Don't use bootstrap class loader directly!
+                        loader = ClassLoader.getSystemClassLoader();
+                    }
+
+                    return loader;
                 }
             }
         );
     }
 
-
     /**
      * Given an enumeration of URLs, an instance of this class represents
      * an enumeration of their InputStreams.  Each operation on the URL
--- a/jdk/src/share/classes/com/sun/nio/sctp/SctpChannel.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/nio/sctp/SctpChannel.java	Fri Jan 10 15:04:46 2014 +0000
@@ -276,6 +276,11 @@
      *
      * @throws  IOException
      *          If some other I/O error occurs
+     *
+     * @throws  SecurityException
+     *          If a security manager has been installed and its
+     *          {@link SecurityManager#checkListen checkListen} method denies
+     *          the operation
      */
     public abstract SctpChannel bind(SocketAddress local)
         throws IOException;
--- a/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/Canonicalizer11.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/Canonicalizer11.java	Fri Jan 10 15:04:46 2014 +0000
@@ -382,7 +382,8 @@
             } else if (!isVisible(xmlns)) {
                 //There is a definition but the xmlns is not selected by the xpath.
                 //then xmlns=""
-                n = ns.addMappingAndRender(XMLNS, "", nullNode);
+                n = ns.addMappingAndRender(
+                        XMLNS, "", getNullNode(xmlns.getOwnerDocument()));
             }
             //output the xmlns def if needed.
             if (n != null) {
--- a/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/Canonicalizer20010315.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/Canonicalizer20010315.java	Fri Jan 10 15:04:46 2014 +0000
@@ -327,7 +327,8 @@
             } else if (!isVisible(xmlns)) {
                 //There is a definition but the xmlns is not selected by the xpath.
                 //then xmlns=""
-                n = ns.addMappingAndRender(XMLNS, "", nullNode);
+                n = ns.addMappingAndRender(
+                        XMLNS, "", getNullNode(xmlns.getOwnerDocument()));
             }
             //output the xmlns def if needed.
             if (n != null) {
--- a/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/Canonicalizer20010315Excl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/Canonicalizer20010315Excl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -292,7 +292,7 @@
             if (xmlns != null && !isVisible(xmlns)) {
                 // There is a definition but the xmlns is not selected by the
                 // xpath. then xmlns=""
-                ns.addMapping(XMLNS, "", nullNode);
+                ns.addMapping(XMLNS, "", getNullNode(xmlns.getOwnerDocument()));
             }
 
             String prefix = null;
--- a/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/CanonicalizerBase.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/org/apache/xml/internal/security/c14n/implementations/CanonicalizerBase.java	Fri Jan 10 15:04:46 2014 +0000
@@ -34,8 +34,6 @@
 import java.util.Map;
 import java.util.Set;
 
-import javax.xml.parsers.DocumentBuilder;
-import javax.xml.parsers.DocumentBuilderFactory;
 import javax.xml.parsers.ParserConfigurationException;
 
 import com.sun.org.apache.xml.internal.security.c14n.CanonicalizationException;
@@ -49,6 +47,7 @@
 import org.w3c.dom.Attr;
 import org.w3c.dom.Comment;
 import org.w3c.dom.Element;
+import org.w3c.dom.Document;
 import org.w3c.dom.NamedNodeMap;
 import org.w3c.dom.Node;
 import org.w3c.dom.ProcessingInstruction;
@@ -64,8 +63,9 @@
     public static final String XMLNS = "xmlns";
 
     protected static final AttrCompare COMPARE = new AttrCompare();
-    protected static final Attr nullNode;
 
+    // Make sure you clone the following mutable arrays before passing to
+    // potentially untrusted objects such as OutputStreams.
     private static final byte[] END_PI = {'?','>'};
     private static final byte[] BEGIN_PI = {'<','?'};
     private static final byte[] END_COMM = {'-','-','>'};
@@ -78,27 +78,17 @@
     private static final byte[] LT = {'&','l','t',';'};
     private static final byte[] END_TAG = {'<','/'};
     private static final byte[] AMP = {'&','a','m','p',';'};
-    private static final byte[] equalsStr = {'=','\"'};
+    private static final byte[] EQUALS_STR = {'=','\"'};
 
     protected static final int NODE_BEFORE_DOCUMENT_ELEMENT = -1;
     protected static final int NODE_NOT_BEFORE_OR_AFTER_DOCUMENT_ELEMENT = 0;
     protected static final int NODE_AFTER_DOCUMENT_ELEMENT = 1;
 
-    static {
-        // The null xmlns definition.
-        try {
-            DocumentBuilder documentBuilder = DocumentBuilderFactory.newInstance().newDocumentBuilder();
-            nullNode = documentBuilder.newDocument().createAttributeNS(Constants.NamespaceSpecNS, XMLNS);
-            nullNode.setValue("");
-        } catch (Exception e) {
-            throw new RuntimeException("Unable to create nullNode: " + e);
-        }
-    }
-
     private List<NodeFilter> nodeFilter;
 
     private boolean includeComments;
     private Set<Node> xpathNodeSet;
+
     /**
      * The node to be skipped/excluded from the DOM tree
      * in subtree canonicalizations.
@@ -107,6 +97,11 @@
     private OutputStream writer = new ByteArrayOutputStream();
 
     /**
+     * The null xmlns definition.
+     */
+    private Attr nullNode;
+
+    /**
      * Constructor CanonicalizerBase
      *
      * @param includeComments
@@ -310,7 +305,7 @@
                 writer.write('>');
                 sibling = currentNode.getFirstChild();
                 if (sibling == null) {
-                    writer.write(END_TAG);
+                    writer.write(END_TAG.clone());
                     UtfHelpper.writeStringToUtf8(name, writer);
                     writer.write('>');
                     //We finished with this level, pop to the previous definitions.
@@ -328,7 +323,7 @@
                 break;
             }
             while (sibling == null && parentNode != null) {
-                writer.write(END_TAG);
+                writer.write(END_TAG.clone());
                 UtfHelpper.writeByte(((Element)parentNode).getTagName(), writer, cache);
                 writer.write('>');
                 //We finished with this level, pop to the previous definitions.
@@ -488,7 +483,7 @@
 
                 if (sibling == null) {
                     if (currentNodeIsVisible) {
-                        writer.write(END_TAG);
+                        writer.write(END_TAG.clone());
                         UtfHelpper.writeByte(name, writer, cache);
                         writer.write('>');
                         //We finished with this level, pop to the previous definitions.
@@ -510,7 +505,7 @@
             }
             while (sibling == null && parentNode != null) {
                 if (isVisible(parentNode)) {
-                    writer.write(END_TAG);
+                    writer.write(END_TAG.clone());
                     UtfHelpper.writeByte(((Element)parentNode).getTagName(), writer, cache);
                     writer.write('>');
                     //We finished with this level, pop to the previous definitions.
@@ -641,8 +636,9 @@
         parents.clear();
         Attr nsprefix;
         if (((nsprefix = ns.getMappingWithoutRendered(XMLNS)) != null)
-            && "".equals(nsprefix.getValue())) {
-            ns.addMappingAndRender(XMLNS, "", nullNode);
+                && "".equals(nsprefix.getValue())) {
+            ns.addMappingAndRender(
+                    XMLNS, "", getNullNode(nsprefix.getOwnerDocument()));
         }
     }
 
@@ -696,7 +692,7 @@
     ) throws IOException {
         writer.write(' ');
         UtfHelpper.writeByte(name, writer, cache);
-        writer.write(equalsStr);
+        writer.write(EQUALS_STR.clone());
         byte[] toWrite;
         final int length = value.length();
         int i = 0;
@@ -706,27 +702,27 @@
             switch (c) {
 
             case '&' :
-                toWrite = AMP;
+                toWrite = AMP.clone();
                 break;
 
             case '<' :
-                toWrite = LT;
+                toWrite = LT.clone();
                 break;
 
             case '"' :
-                toWrite = QUOT;
+                toWrite = QUOT.clone();
                 break;
 
             case 0x09 :    // '\t'
-                toWrite = X9;
+                toWrite = X9.clone();
                 break;
 
             case 0x0A :    // '\n'
-                toWrite = XA;
+                toWrite = XA.clone();
                 break;
 
             case 0x0D :    // '\r'
-                toWrite = XD;
+                toWrite = XD.clone();
                 break;
 
             default :
@@ -756,7 +752,7 @@
         if (position == NODE_AFTER_DOCUMENT_ELEMENT) {
             writer.write('\n');
         }
-        writer.write(BEGIN_PI);
+        writer.write(BEGIN_PI.clone());
 
         final String target = currentPI.getTarget();
         int length = target.length();
@@ -764,7 +760,7 @@
         for (int i = 0; i < length; i++) {
             char c = target.charAt(i);
             if (c == 0x0D) {
-                writer.write(XD);
+                writer.write(XD.clone());
             } else {
                 if (c < 0x80) {
                     writer.write(c);
@@ -784,14 +780,14 @@
             for (int i = 0; i < length; i++) {
                 char c = data.charAt(i);
                 if (c == 0x0D) {
-                    writer.write(XD);
+                    writer.write(XD.clone());
                 } else {
                     UtfHelpper.writeCharToUtf8(c, writer);
                 }
             }
         }
 
-        writer.write(END_PI);
+        writer.write(END_PI.clone());
         if (position == NODE_BEFORE_DOCUMENT_ELEMENT) {
             writer.write('\n');
         }
@@ -810,7 +806,7 @@
         if (position == NODE_AFTER_DOCUMENT_ELEMENT) {
             writer.write('\n');
         }
-        writer.write(BEGIN_COMM);
+        writer.write(BEGIN_COMM.clone());
 
         final String data = currentComment.getData();
         final int length = data.length();
@@ -818,7 +814,7 @@
         for (int i = 0; i < length; i++) {
             char c = data.charAt(i);
             if (c == 0x0D) {
-                writer.write(XD);
+                writer.write(XD.clone());
             } else {
                 if (c < 0x80) {
                     writer.write(c);
@@ -828,7 +824,7 @@
             }
         }
 
-        writer.write(END_COMM);
+        writer.write(END_COMM.clone());
         if (position == NODE_BEFORE_DOCUMENT_ELEMENT) {
             writer.write('\n');
         }
@@ -852,19 +848,19 @@
             switch (c) {
 
             case '&' :
-                toWrite = AMP;
+                toWrite = AMP.clone();
                 break;
 
             case '<' :
-                toWrite = LT;
+                toWrite = LT.clone();
                 break;
 
             case '>' :
-                toWrite = GT;
+                toWrite = GT.clone();
                 break;
 
             case 0xD :
-                toWrite = XD;
+                toWrite = XD.clone();
                 break;
 
             default :
@@ -879,4 +875,18 @@
         }
     }
 
+    // The null xmlns definition.
+    protected Attr getNullNode(Document ownerDocument) {
+        if (nullNode == null) {
+            try {
+                nullNode = ownerDocument.createAttributeNS(
+                                    Constants.NamespaceSpecNS, XMLNS);
+                nullNode.setValue("");
+            } catch (Exception e) {
+                throw new RuntimeException("Unable to create nullNode: " + e);
+            }
+        }
+        return nullNode;
+    }
+
 }
--- a/jdk/src/share/classes/com/sun/rowset/internal/XmlReaderContentHandler.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/com/sun/rowset/internal/XmlReaderContentHandler.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -660,7 +660,7 @@
                      //Added the handling for Class tags to take care of maps
                      //Makes an entry into the map upon end of class tag
                      try{
-                          typeMap.put(Key_map,Class.forName(Value_map));
+                          typeMap.put(Key_map,sun.reflect.misc.ReflectUtil.forName(Value_map));
 
                         }catch(ClassNotFoundException ex) {
                           throw new SAXException(MessageFormat.format(resBundle.handleGetObject("xmlrch.errmap").toString(), ex.getMessage()));
--- a/jdk/src/share/classes/java/lang/SecurityManager.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/lang/SecurityManager.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1106,11 +1106,8 @@
      * calling thread is not allowed to wait for a connection request on
      * the specified local port number.
      * <p>
-     * If port is not 0, this method calls
-     * <code>checkPermission</code> with the
+     * This method calls <code>checkPermission</code> with the
      * <code>SocketPermission("localhost:"+port,"listen")</code>.
-     * If port is zero, this method calls <code>checkPermission</code>
-     * with <code>SocketPermission("localhost:1024-","listen").</code>
      * <p>
      * If you override this method, then you should make a call to
      * <code>super.checkListen</code>
@@ -1123,12 +1120,8 @@
      * @see        #checkPermission(java.security.Permission) checkPermission
      */
     public void checkListen(int port) {
-        if (port == 0) {
-            checkPermission(SecurityConstants.LOCAL_LISTEN_PERMISSION);
-        } else {
-            checkPermission(new SocketPermission("localhost:"+port,
-                SecurityConstants.SOCKET_LISTEN_ACTION));
-        }
+        checkPermission(new SocketPermission("localhost:"+port,
+            SecurityConstants.SOCKET_LISTEN_ACTION));
     }
 
     /**
--- a/jdk/src/share/classes/java/net/Socket.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/net/Socket.java	Fri Jan 10 15:04:46 2014 +0000
@@ -272,7 +272,9 @@
      *        {@code zero} for a system selected free port.
      * @exception  IOException  if an I/O error occurs when creating the socket.
      * @exception  SecurityException  if a security manager exists and its
-     *             {@code checkConnect} method doesn't allow the operation.
+     *             {@code checkConnect} method doesn't allow the connection
+     *             to the destination, or if its {@code checkListen} method
+     *             doesn't allow the bind to the local port.
      * @exception  IllegalArgumentException if the port parameter or localPort
      *             parameter is outside the specified range of valid port values,
      *             which is between 0 and 65535, inclusive.
@@ -311,7 +313,9 @@
      *        {@code zero} for a system selected free port.
      * @exception  IOException  if an I/O error occurs when creating the socket.
      * @exception  SecurityException  if a security manager exists and its
-     *             {@code checkConnect} method doesn't allow the operation.
+     *             {@code checkConnect} method doesn't allow the connection
+     *             to the destination, or if its {@code checkListen} method
+     *             doesn't allow the bind to the local port.
      * @exception  IllegalArgumentException if the port parameter or localPort
      *             parameter is outside the specified range of valid port values,
      *             which is between 0 and 65535, inclusive.
@@ -609,6 +613,9 @@
      *                     is already bound.
      * @throws  IllegalArgumentException if bindpoint is a
      *          SocketAddress subclass not supported by this socket
+     * @throws  SecurityException  if a security manager exists and its
+     *          {@code checkListen} method doesn't allow the bind
+     *          to the local port.
      *
      * @since   1.4
      * @see #isBound
@@ -630,6 +637,10 @@
         InetAddress addr = epoint.getAddress();
         int port = epoint.getPort();
         checkAddress (addr, "bind");
+        SecurityManager security = System.getSecurityManager();
+        if (security != null) {
+            security.checkListen(port);
+        }
         getImpl().bind (addr, port);
         bound = true;
     }
--- a/jdk/src/share/classes/java/net/SocketPermission.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/net/SocketPermission.java	Fri Jan 10 15:04:46 2014 +0000
@@ -34,6 +34,9 @@
 import java.net.InetAddress;
 import java.security.Permission;
 import java.security.PermissionCollection;
+import java.security.PrivilegedAction;
+import java.security.AccessController;
+import java.security.Security;
 import java.io.Serializable;
 import java.io.ObjectStreamField;
 import java.io.ObjectOutputStream;
@@ -41,6 +44,7 @@
 import java.io.IOException;
 import sun.net.util.IPAddressUtil;
 import sun.net.RegisteredDomain;
+import sun.net.PortConfig;
 import sun.security.util.SecurityConstants;
 import sun.security.util.Debug;
 
@@ -89,6 +93,9 @@
  * form "N-", where <i>N</i> is a port number, signifies all ports
  * numbered <i>N</i> and above, while a specification of the
  * form "-N" indicates all ports numbered <i>N</i> and below.
+ * The special port value {@code 0} refers to the entire <i>ephemeral</i>
+ * port range. This is a fixed range of ports a system may use to
+ * allocate dynamic ports from. The actual range may be system dependent.
  * <p>
  * The possible ways to connect to the host are
  * <pre>
@@ -97,7 +104,8 @@
  * listen
  * resolve
  * </pre>
- * The "listen" action is only meaningful when used with "localhost".
+ * The "listen" action is only meaningful when used with "localhost" and
+ * means the ability to bind to a specified port.
  * The "resolve" action is implied when any of the other actions are present.
  * The action "resolve" refers to host/ip name service lookups.
  * <P>
@@ -176,6 +184,7 @@
     private static final int PORT_MIN = 0;
     private static final int PORT_MAX = 65535;
     private static final int PRIV_PORT_MAX = 1023;
+    private static final int DEF_EPH_LOW = 49152;
 
     // the actions mask
     private transient int mask;
@@ -226,6 +235,14 @@
     private static Debug debug = null;
     private static boolean debugInit = false;
 
+    // ephemeral port range for this system
+    private static final int ephemeralLow = initEphemeralPorts(
+        "low", DEF_EPH_LOW
+    );
+    private static final int ephemeralHigh = initEphemeralPorts(
+        "high", PORT_MAX
+    );
+
     static {
         Boolean tmp = java.security.AccessController.doPrivileged(
                 new sun.security.action.GetBooleanAction("sun.net.trustNameService"));
@@ -360,6 +377,14 @@
     }
 
     /**
+     * Returns true if the permission has specified zero
+     * as its value (or lower bound) signifying the ephemeral range
+     */
+    private boolean includesEphemerals() {
+        return portrange[0] == 0;
+    }
+
+    /**
      * Initialize the SocketPermission object. We don't do any DNS lookups
      * as this point, instead we hold off until the implies method is
      * called.
@@ -850,10 +875,21 @@
         int i,j;
 
         if ((that.mask & RESOLVE) != that.mask) {
-            // check port range
+
+            // check simple port range
             if ((that.portrange[0] < this.portrange[0]) ||
                     (that.portrange[1] > this.portrange[1])) {
+
+                // if either includes the ephemeral range, do full check
+                if (this.includesEphemerals() || that.includesEphemerals()) {
+                    if (!inRange(this.portrange[0], this.portrange[1],
+                                     that.portrange[0], that.portrange[1]))
+                    {
+                                return false;
+                    }
+                } else {
                     return false;
+                }
             }
         }
 
@@ -1168,6 +1204,75 @@
         init(getName(),getMask(actions));
     }
 
+    /**
+     * Check the system/security property for the ephemeral port range
+     * for this system. The suffix is either "high" or "low"
+     */
+    private static int initEphemeralPorts(String suffix, int defval) {
+        return AccessController.doPrivileged(
+            new PrivilegedAction<Integer>(){
+                public Integer run() {
+                    int val = Integer.getInteger(
+                            "jdk.net.ephemeralPortRange."+suffix, -1
+                    );
+                    if (val != -1) {
+                        return val;
+                    } else {
+                        return suffix.equals("low") ?
+                            PortConfig.getLower() : PortConfig.getUpper();
+                    }
+                }
+            }
+        );
+    }
+
+    /**
+     * Check if the target range is within the policy range
+     * together with the ephemeral range for this platform
+     * (if policy includes ephemeral range)
+     */
+    private static boolean inRange(
+        int policyLow, int policyHigh, int targetLow, int targetHigh
+    )
+    {
+        if (targetLow == 0) {
+            // check policy includes ephemeral range
+            if (!inRange(policyLow, policyHigh, ephemeralLow, ephemeralHigh)) {
+                return false;
+            }
+            if (targetHigh == 0) {
+                // nothing left to do
+                return true;
+            }
+            // continue check with first real port number
+            targetLow = 1;
+        }
+
+        if (policyLow == 0 && policyHigh == 0) {
+            // ephemeral range only
+            return targetLow >= ephemeralLow && targetHigh <= ephemeralHigh;
+        }
+
+        if (policyLow != 0) {
+            // simple check of policy only
+            return targetLow >= policyLow && targetHigh <= policyHigh;
+        }
+
+        // policyLow == 0 which means possibly two ranges to check
+
+        // first check if policy and ephem range overlap/contiguous
+
+        if (policyHigh >= ephemeralLow - 1) {
+            return targetHigh <= ephemeralHigh;
+        }
+
+        // policy and ephem range do not overlap
+
+        // target range must lie entirely inside policy range or eph range
+
+        return  (targetLow <= policyHigh && targetHigh <= policyHigh) ||
+                (targetLow >= ephemeralLow && targetHigh <= ephemeralHigh);
+    }
     /*
     public String toString()
     {
--- a/jdk/src/share/classes/java/nio/channels/AsynchronousSocketChannel.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/nio/channels/AsynchronousSocketChannel.java	Fri Jan 10 15:04:46 2014 +0000
@@ -200,6 +200,10 @@
      * @throws  UnsupportedAddressTypeException     {@inheritDoc}
      * @throws  ClosedChannelException              {@inheritDoc}
      * @throws  IOException                         {@inheritDoc}
+     * @throws  SecurityException
+     *          If a security manager has been installed and its
+     *          {@link SecurityManager#checkListen checkListen} method denies
+     *          the operation
      */
     @Override
     public abstract AsynchronousSocketChannel bind(SocketAddress local)
--- a/jdk/src/share/classes/java/nio/channels/SocketChannel.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/nio/channels/SocketChannel.java	Fri Jan 10 15:04:46 2014 +0000
@@ -227,6 +227,10 @@
      * @throws  UnsupportedAddressTypeException     {@inheritDoc}
      * @throws  ClosedChannelException              {@inheritDoc}
      * @throws  IOException                         {@inheritDoc}
+     * @throws  SecurityException
+     *          If a security manager has been installed and its
+     *          {@link SecurityManager#checkListen checkListen} method denies
+     *          the operation
      *
      * @since 1.7
      */
--- a/jdk/src/share/classes/java/util/jar/JarFile.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/util/jar/JarFile.java	Fri Jan 10 15:04:46 2014 +0000
@@ -53,6 +53,13 @@
  * or method in this class will cause a {@link NullPointerException} to be
  * thrown.
  *
+ * If the verify flag is on when opening a signed jar file, the content of the
+ * file is verified against its signature embedded inside the file. Please note
+ * that the verification process does not include validating the signer's
+ * certificate. A caller should inspect the return value of
+ * {@link JarEntry#getCodeSigners()} to further determine if the signature
+ * can be trusted.
+ *
  * @author  David Connelly
  * @see     Manifest
  * @see     java.util.zip.ZipFile
--- a/jdk/src/share/classes/java/util/jar/JarVerifier.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/util/jar/JarVerifier.java	Fri Jan 10 15:04:46 2014 +0000
@@ -179,7 +179,9 @@
             name = name.substring(1);
 
         // only set the jev object for entries that have a signature
-        if (sigFileSigners.get(name) != null) {
+        // (either verified or not)
+        if (sigFileSigners.get(name) != null ||
+                verifiedSigners.get(name) != null) {
             mev.setEntry(name, je);
             return;
         }
--- a/jdk/src/share/classes/java/util/logging/LogManager.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/java/util/logging/LogManager.java	Fri Jan 10 15:04:46 2014 +0000
@@ -240,6 +240,11 @@
      * retrieved by calling LogManager.getLogManager.
      */
     protected LogManager() {
+        this(checkSubclassPermissions());
+    }
+
+    private LogManager(Void checked) {
+
         // Add a shutdown hook to close the global handlers.
         try {
             Runtime.getRuntime().addShutdownHook(new Cleaner());
@@ -249,6 +254,19 @@
         }
     }
 
+    private static Void checkSubclassPermissions() {
+        final SecurityManager sm = System.getSecurityManager();
+        if (sm != null) {
+            // These permission will be checked in the LogManager constructor,
+            // in order to register the Cleaner() thread as a shutdown hook.
+            // Check them here to avoid the penalty of constructing the object
+            // etc...
+            sm.checkPermission(new RuntimePermission("shutdownHooks"));
+            sm.checkPermission(new RuntimePermission("setContextClassLoader"));
+        }
+        return null;
+    }
+
     /**
      * Lazy initialization: if this instance of manager is the global
      * manager then this method will read the initial configuration and
--- a/jdk/src/share/classes/javax/print/SimpleDoc.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/print/SimpleDoc.java	Fri Jan 10 15:04:46 2014 +0000
@@ -91,7 +91,10 @@
 
        Class repClass = null;
        try {
-            repClass = Class.forName(flavor.getRepresentationClassName());
+            String className = flavor.getRepresentationClassName();
+            sun.reflect.misc.ReflectUtil.checkPackageAccess(className);
+            repClass = Class.forName(className, false,
+                              Thread.currentThread().getContextClassLoader());
        } catch (Throwable e) {
            throw new IllegalArgumentException("unknown representation class");
        }
--- a/jdk/src/share/classes/javax/security/auth/Policy.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/security/auth/Policy.java	Fri Jan 10 15:04:46 2014 +0000
@@ -26,6 +26,10 @@
 package javax.security.auth;
 
 import java.security.Security;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.security.PrivilegedExceptionAction;
+import java.util.Objects;
 import sun.security.util.Debug;
 
 /**
@@ -155,22 +159,15 @@
 public abstract class Policy {
 
     private static Policy policy;
-    private static ClassLoader contextClassLoader;
     private final static String AUTH_POLICY =
         "sun.security.provider.AuthPolicyFile";
 
+    private final java.security.AccessControlContext acc =
+            java.security.AccessController.getContext();
+
     // true if a custom (not AUTH_POLICY) system-wide policy object is set
     private static boolean isCustomPolicy;
 
-    static {
-        contextClassLoader = java.security.AccessController.doPrivileged
-                (new java.security.PrivilegedAction<ClassLoader>() {
-                public ClassLoader run() {
-                    return Thread.currentThread().getContextClassLoader();
-                }
-        });
-    };
-
     /**
      * Sole constructor.  (For invocation by subclass constructors, typically
      * implicit.)
@@ -213,8 +210,8 @@
 
                 if (policy == null) {
                     String policy_class = null;
-                    policy_class = java.security.AccessController.doPrivileged
-                        (new java.security.PrivilegedAction<String>() {
+                    policy_class = AccessController.doPrivileged
+                        (new PrivilegedAction<String>() {
                         public String run() {
                             return java.security.Security.getProperty
                                 ("auth.policy.provider");
@@ -226,18 +223,28 @@
 
                     try {
                         final String finalClass = policy_class;
-                        policy = java.security.AccessController.doPrivileged
-                            (new java.security.PrivilegedExceptionAction<Policy>() {
-                            public Policy run() throws ClassNotFoundException,
-                                                InstantiationException,
-                                                IllegalAccessException {
-                                return (Policy) Class.forName
-                                        (finalClass,
-                                        true,
-                                        contextClassLoader).newInstance();
-                            }
-                        });
-                        isCustomPolicy = !finalClass.equals(AUTH_POLICY);
+
+                        Policy untrustedImpl = AccessController.doPrivileged(
+                                new PrivilegedExceptionAction<Policy>() {
+                                    public Policy run() throws ClassNotFoundException,
+                                            InstantiationException,
+                                            IllegalAccessException {
+                                        Class<? extends Policy> implClass = Class.forName(
+                                                finalClass, false,
+                                                Thread.currentThread().getContextClassLoader()
+                                        ).asSubclass(Policy.class);
+                                        return implClass.newInstance();
+                                    }
+                                });
+                        AccessController.doPrivileged(
+                                new PrivilegedExceptionAction<Void>() {
+                                    public Void run() {
+                                        setPolicy(untrustedImpl);
+                                        isCustomPolicy = !finalClass.equals(AUTH_POLICY);
+                                        return null;
+                                    }
+                                }, Objects.requireNonNull(untrustedImpl.acc)
+                        );
                     } catch (Exception e) {
                         throw new SecurityException
                                 (sun.security.util.ResourcesMgr.getString
--- a/jdk/src/share/classes/javax/security/auth/Subject.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/security/auth/Subject.java	Fri Jan 10 15:04:46 2014 +0000
@@ -964,6 +964,10 @@
 
         s.defaultReadObject();
 
+        // Rewrap the principals into a SecureSet
+        principals = Collections.synchronizedSet(new SecureSet<Principal>
+                                (this, PRINCIPAL_SET, principals));
+
         // The Credential {@code Set} is not serialized, but we do not
         // want the default deserialization routine to set it to null.
         this.pubCredentials = Collections.synchronizedSet
--- a/jdk/src/share/classes/javax/security/auth/login/Configuration.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/security/auth/login/Configuration.java	Fri Jan 10 15:04:46 2014 +0000
@@ -27,9 +27,6 @@
 
 import javax.security.auth.AuthPermission;
 
-import java.io.*;
-import java.util.*;
-import java.net.URI;
 import java.security.AccessController;
 import java.security.PrivilegedAction;
 import java.security.PrivilegedExceptionAction;
@@ -38,7 +35,7 @@
 import java.security.NoSuchProviderException;
 import java.security.Provider;
 import java.security.Security;
-import java.security.SecurityPermission;
+import java.util.Objects;
 
 import sun.security.jca.GetInstance;
 
@@ -191,16 +188,9 @@
 public abstract class Configuration {
 
     private static Configuration configuration;
-    private static ClassLoader contextClassLoader;
 
-    static {
-        contextClassLoader = AccessController.doPrivileged
-                (new PrivilegedAction<ClassLoader>() {
-                public ClassLoader run() {
-                    return Thread.currentThread().getContextClassLoader();
-                }
-        });
-    };
+    private final java.security.AccessControlContext acc =
+            java.security.AccessController.getContext();
 
     private static void checkPermission(String type) {
         SecurityManager sm = System.getSecurityManager();
@@ -253,17 +243,26 @@
 
                 try {
                     final String finalClass = config_class;
-                    configuration = AccessController.doPrivileged
-                        (new PrivilegedExceptionAction<Configuration>() {
-                        public Configuration run() throws ClassNotFoundException,
-                                            InstantiationException,
-                                            IllegalAccessException {
-                            return (Configuration)Class.forName
-                                    (finalClass,
-                                    true,
-                                    contextClassLoader).newInstance();
-                        }
-                    });
+                    Configuration untrustedImpl = AccessController.doPrivileged(
+                            new PrivilegedExceptionAction<Configuration>() {
+                                public Configuration run() throws ClassNotFoundException,
+                                        InstantiationException,
+                                        IllegalAccessException {
+                                    Class<? extends Configuration> implClass = Class.forName(
+                                            finalClass, false,
+                                            Thread.currentThread().getContextClassLoader()
+                                    ).asSubclass(Configuration.class);
+                                    return implClass.newInstance();
+                                }
+                            });
+                    AccessController.doPrivileged(
+                            new PrivilegedExceptionAction<Void>() {
+                                public Void run() {
+                                    setConfiguration(untrustedImpl);
+                                    return null;
+                                }
+                            }, Objects.requireNonNull(untrustedImpl.acc)
+                    );
                 } catch (PrivilegedActionException e) {
                     Exception ee = e.getException();
                     if (ee instanceof InstantiationException) {
--- a/jdk/src/share/classes/javax/security/auth/login/LoginContext.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/security/auth/login/LoginContext.java	Fri Jan 10 15:04:46 2014 +0000
@@ -209,8 +209,7 @@
     private Map<String,?> state = new HashMap<String,Object>();
 
     private Configuration config;
-    private boolean configProvided = false;
-    private AccessControlContext creatorAcc = null;
+    private AccessControlContext creatorAcc = null;  // customized config only
     private ModuleInfo[] moduleStack;
     private ClassLoader contextClassLoader = null;
     private static final Class<?>[] PARAMS = { };
@@ -229,7 +228,7 @@
     private void init(String name) throws LoginException {
 
         SecurityManager sm = System.getSecurityManager();
-        if (sm != null && !configProvided) {
+        if (sm != null && creatorAcc == null) {
             sm.checkPermission(new AuthPermission
                                 ("createLoginContext." + name));
         }
@@ -252,7 +251,7 @@
         AppConfigurationEntry[] entries = config.getAppConfigurationEntry(name);
         if (entries == null) {
 
-            if (sm != null && !configProvided) {
+            if (sm != null && creatorAcc == null) {
                 sm.checkPermission(new AuthPermission
                                 ("createLoginContext." + OTHER));
             }
@@ -279,7 +278,15 @@
         contextClassLoader = java.security.AccessController.doPrivileged
                 (new java.security.PrivilegedAction<ClassLoader>() {
                 public ClassLoader run() {
-                    return Thread.currentThread().getContextClassLoader();
+                    ClassLoader loader =
+                            Thread.currentThread().getContextClassLoader();
+                    if (loader == null) {
+                        // Don't use bootstrap class loader directly to ensure
+                        // proper package access control!
+                        loader = ClassLoader.getSystemClassLoader();
+                    }
+
+                    return loader;
                 }
         });
     }
@@ -298,10 +305,10 @@
                         (DEFAULT_HANDLER);
                     if (defaultHandler == null || defaultHandler.length() == 0)
                         return null;
-                    Class<?> c = Class.forName(defaultHandler,
-                                        true,
-                                        finalLoader);
-                    return (CallbackHandler)c.newInstance();
+                    Class<? extends CallbackHandler> c = Class.forName(
+                            defaultHandler, true,
+                            finalLoader).asSubclass(CallbackHandler.class);
+                    return c.newInstance();
                 }
             });
         } catch (java.security.PrivilegedActionException pae) {
@@ -309,7 +316,7 @@
         }
 
         // secure it with the caller's ACC
-        if (this.callbackHandler != null && !configProvided) {
+        if (this.callbackHandler != null && creatorAcc == null) {
             this.callbackHandler = new SecureCallbackHandler
                                 (java.security.AccessController.getContext(),
                                 this.callbackHandler);
@@ -498,8 +505,7 @@
                         CallbackHandler callbackHandler,
                         Configuration config) throws LoginException {
         this.config = config;
-        configProvided = (config != null) ? true : false;
-        if (configProvided) {
+        if (config != null) {
             creatorAcc = java.security.AccessController.getContext();
         }
 
@@ -510,7 +516,7 @@
         }
         if (callbackHandler == null) {
             loadDefaultCallbackHandler();
-        } else if (!configProvided) {
+        } else if (creatorAcc == null) {
             this.callbackHandler = new SecureCallbackHandler
                                 (java.security.AccessController.getContext(),
                                 callbackHandler);
@@ -577,23 +583,13 @@
         }
 
         try {
-            if (configProvided) {
-                // module invoked in doPrivileged with creatorAcc
-                invokeCreatorPriv(LOGIN_METHOD);
-                invokeCreatorPriv(COMMIT_METHOD);
-            } else {
-                // module invoked in doPrivileged
-                invokePriv(LOGIN_METHOD);
-                invokePriv(COMMIT_METHOD);
-            }
+            // module invoked in doPrivileged
+            invokePriv(LOGIN_METHOD);
+            invokePriv(COMMIT_METHOD);
             loginSucceeded = true;
         } catch (LoginException le) {
             try {
-                if (configProvided) {
-                    invokeCreatorPriv(ABORT_METHOD);
-                } else {
-                    invokePriv(ABORT_METHOD);
-                }
+                invokePriv(ABORT_METHOD);
             } catch (LoginException le2) {
                 throw le;
             }
@@ -628,13 +624,8 @@
                 ("null.subject.logout.called.before.login"));
         }
 
-        if (configProvided) {
-            // module invoked in doPrivileged with creatorAcc
-            invokeCreatorPriv(LOGOUT_METHOD);
-        } else {
-            // module invoked in doPrivileged
-            invokePriv(LOGOUT_METHOD);
-        }
+        // module invoked in doPrivileged
+        invokePriv(LOGOUT_METHOD);
     }
 
     /**
@@ -677,7 +668,8 @@
 
     /**
      * Invokes the login, commit, and logout methods
-     * from a LoginModule inside a doPrivileged block.
+     * from a LoginModule inside a doPrivileged block restricted
+     * by creatorAcc (may be null).
      *
      * This version is called if the caller did not instantiate
      * the LoginContext with a Configuration object.
@@ -690,29 +682,6 @@
                     invoke(methodName);
                     return null;
                 }
-            });
-        } catch (java.security.PrivilegedActionException pae) {
-            throw (LoginException)pae.getException();
-        }
-    }
-
-    /**
-     * Invokes the login, commit, and logout methods
-     * from a LoginModule inside a doPrivileged block restricted
-     * by creatorAcc
-     *
-     * This version is called if the caller instantiated
-     * the LoginContext with a Configuration object.
-     */
-    private void invokeCreatorPriv(final String methodName)
-                throws LoginException {
-        try {
-            java.security.AccessController.doPrivileged
-                (new java.security.PrivilegedExceptionAction<Void>() {
-                public Void run() throws LoginException {
-                    invoke(methodName);
-                    return null;
-                }
             }, creatorAcc);
         } catch (java.security.PrivilegedActionException pae) {
             throw (LoginException)pae.getException();
@@ -735,24 +704,24 @@
                 } else {
 
                     // instantiate the LoginModule
-                    Class<?> c = Class.forName
-                                (moduleStack[i].entry.getLoginModuleName(),
+                    //
+                    // Allow any object to be a LoginModule as long as it
+                    // conforms to the interface.
+                    Class<?> c = Class.forName(
+                                moduleStack[i].entry.getLoginModuleName(),
                                 true,
                                 contextClassLoader);
 
                     Constructor<?> constructor = c.getConstructor(PARAMS);
                     Object[] args = { };
-
-                    // allow any object to be a LoginModule
-                    // as long as it conforms to the interface
                     moduleStack[i].module = constructor.newInstance(args);
 
+                    // call the LoginModule's initialize method
                     methods = moduleStack[i].module.getClass().getMethods();
-
-                    // call the LoginModule's initialize method
                     for (mIndex = 0; mIndex < methods.length; mIndex++) {
-                        if (methods[mIndex].getName().equals(INIT_METHOD))
+                        if (methods[mIndex].getName().equals(INIT_METHOD)) {
                             break;
+                        }
                     }
 
                     Object[] initArgs = {subject,
@@ -760,19 +729,28 @@
                                         state,
                                         moduleStack[i].entry.getOptions() };
                     // invoke the LoginModule initialize method
+                    //
+                    // Throws ArrayIndexOutOfBoundsException if no such
+                    // method defined.  May improve to use LoginException in
+                    // the future.
                     methods[mIndex].invoke(moduleStack[i].module, initArgs);
                 }
 
                 // find the requested method in the LoginModule
                 for (mIndex = 0; mIndex < methods.length; mIndex++) {
-                    if (methods[mIndex].getName().equals(methodName))
+                    if (methods[mIndex].getName().equals(methodName)) {
                         break;
+                    }
                 }
 
                 // set up the arguments to be passed to the LoginModule method
                 Object[] args = { };
 
                 // invoke the LoginModule method
+                //
+                // Throws ArrayIndexOutOfBoundsException if no such
+                // method defined.  May improve to use LoginException in
+                // the future.
                 boolean status = ((Boolean)methods[mIndex].invoke
                                 (moduleStack[i].module, args)).booleanValue();
 
--- a/jdk/src/share/classes/javax/sql/rowset/spi/SyncFactory.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/sql/rowset/spi/SyncFactory.java	Fri Jan 10 15:04:46 2014 +0000
@@ -35,6 +35,8 @@
 import java.io.InputStream;
 import java.io.IOException;
 import java.io.FileNotFoundException;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
 
 import javax.naming.*;
 
@@ -348,7 +350,17 @@
                 /*
                  * Dependent on application
                  */
-                String strRowsetProperties = System.getProperty("rowset.properties");
+                String strRowsetProperties;
+                try {
+                    strRowsetProperties = AccessController.doPrivileged(new PrivilegedAction<String>() {
+                        public String run() {
+                            return System.getProperty("rowset.properties");
+                        }
+                    }, null, new PropertyPermission("rowset.properties","read"));
+                } catch (Exception ex) {
+                    strRowsetProperties = null;
+                }
+
                 if (strRowsetProperties != null) {
                     // Load user's implementation of SyncProvider
                     // here. -Drowset.properties=/abc/def/pqr.txt
@@ -393,7 +405,16 @@
              * load additional properties from -D command line
              */
             properties.clear();
-            String providerImpls = System.getProperty(ROWSET_SYNC_PROVIDER);
+            String providerImpls;
+            try {
+                providerImpls = AccessController.doPrivileged(new PrivilegedAction<String>() {
+                    public String run() {
+                        return System.getProperty(ROWSET_SYNC_PROVIDER);
+                    }
+                }, null, new PropertyPermission(ROWSET_SYNC_PROVIDER,"read"));
+            } catch (Exception ex) {
+                providerImpls = null;
+            }
 
             if (providerImpls != null) {
                 int i = 0;
--- a/jdk/src/share/classes/javax/swing/SwingUtilities.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/swing/SwingUtilities.java	Fri Jan 10 15:04:46 2014 +0000
@@ -24,6 +24,7 @@
  */
 package javax.swing;
 
+import sun.reflect.misc.ReflectUtil;
 import sun.swing.SwingUtilities2;
 import sun.swing.UIAction;
 
@@ -33,9 +34,6 @@
 import java.awt.event.*;
 import java.awt.dnd.DropTarget;
 
-import java.util.Vector;
-import java.util.Hashtable;
-
 import java.lang.reflect.*;
 
 import javax.accessibility.*;
@@ -1872,6 +1870,7 @@
 
 
     static Class<?> loadSystemClass(String className) throws ClassNotFoundException {
+        ReflectUtil.checkPackageAccess(className);
         return Class.forName(className, true, Thread.currentThread().
                              getContextClassLoader());
     }
--- a/jdk/src/share/classes/javax/swing/event/EventListenerList.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/javax/swing/event/EventListenerList.java	Fri Jan 10 15:04:46 2014 +0000
@@ -27,6 +27,7 @@
 import java.io.*;
 import java.util.*;
 import java.lang.reflect.Array;
+import sun.reflect.misc.ReflectUtil;
 
 /**
  * A class that holds a list of EventListeners.  A single instance
@@ -271,7 +272,9 @@
         while (null != (listenerTypeOrNull = s.readObject())) {
             ClassLoader cl = Thread.currentThread().getContextClassLoader();
             EventListener l = (EventListener)s.readObject();
-            add((Class<EventListener>)Class.forName((String)listenerTypeOrNull, true, cl), l);
+            String name = (String) listenerTypeOrNull;
+            ReflectUtil.checkPackageAccess(name);
+            add((Class<EventListener>)Class.forName(name, true, cl), l);
         }
     }
 
--- a/jdk/src/share/classes/sun/nio/ch/AsynchronousSocketChannelImpl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/nio/ch/AsynchronousSocketChannelImpl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -428,6 +428,10 @@
                     throw new AlreadyBoundException();
                 InetSocketAddress isa = (local == null) ?
                     new InetSocketAddress(0) : Net.checkAddress(local);
+                SecurityManager sm = System.getSecurityManager();
+                if (sm != null) {
+                    sm.checkListen(isa.getPort());
+                }
                 NetHooks.beforeTcpBind(fd, isa.getAddress(), isa.getPort());
                 Net.bind(fd, isa.getAddress(), isa.getPort());
                 localAddress = Net.localAddress(fd);
--- a/jdk/src/share/classes/sun/nio/ch/SocketChannelImpl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/nio/ch/SocketChannelImpl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -572,6 +572,10 @@
                         throw new AlreadyBoundException();
                     InetSocketAddress isa = (local == null) ?
                         new InetSocketAddress(0) : Net.checkAddress(local);
+                    SecurityManager sm = System.getSecurityManager();
+                    if (sm != null) {
+                        sm.checkListen(isa.getPort());
+                    }
                     NetHooks.beforeTcpBind(fd, isa.getAddress(), isa.getPort());
                     Net.bind(fd, isa.getAddress(), isa.getPort());
                     localAddress = Net.localAddress(fd);
--- a/jdk/src/share/classes/sun/reflect/generics/reflectiveObjects/TypeVariableImpl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/reflect/generics/reflectiveObjects/TypeVariableImpl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -28,7 +28,10 @@
 import java.lang.annotation.*;
 import java.lang.reflect.AnnotatedType;
 import java.lang.reflect.Array;
+import java.lang.reflect.Constructor;
 import java.lang.reflect.GenericDeclaration;
+import java.lang.reflect.Member;
+import java.lang.reflect.Method;
 import java.lang.reflect.Type;
 import java.lang.reflect.TypeVariable;
 import java.util.LinkedHashMap;
@@ -40,6 +43,7 @@
 import sun.reflect.generics.factory.GenericsFactory;
 import sun.reflect.generics.tree.FieldTypeSignature;
 import sun.reflect.generics.visitor.Reifier;
+import sun.reflect.misc.ReflectUtil;
 
 /**
  * Implementation of <tt>java.lang.reflect.TypeVariable</tt> interface
@@ -95,6 +99,13 @@
                              TypeVariableImpl<T> make(T decl, String name,
                                                       FieldTypeSignature[] bs,
                                                       GenericsFactory f) {
+
+        if (!((decl instanceof Class) ||
+                (decl instanceof Method) ||
+                (decl instanceof Constructor))) {
+            throw new AssertionError("Unexpected kind of GenericDeclaration" +
+                    decl.getClass().toString());
+        }
         return new TypeVariableImpl<T>(decl, name, bs, f);
     }
 
@@ -149,6 +160,13 @@
      * @since 1.5
      */
     public D getGenericDeclaration(){
+        if (genericDeclaration instanceof Class)
+            ReflectUtil.checkPackageAccess((Class)genericDeclaration);
+        else if ((genericDeclaration instanceof Method) ||
+                (genericDeclaration instanceof Constructor))
+            ReflectUtil.conservativeCheckMemberAccess((Member)genericDeclaration);
+        else
+            throw new AssertionError("Unexpected kind of GenericDeclaration");
         return genericDeclaration;
     }
 
@@ -164,7 +182,8 @@
 
     @Override
     public boolean equals(Object o) {
-        if (o instanceof TypeVariable) {
+        if (o instanceof TypeVariable &&
+                o.getClass() == TypeVariableImpl.class) {
             TypeVariable<?> that = (TypeVariable<?>) o;
 
             GenericDeclaration thatDecl = that.getGenericDeclaration();
--- a/jdk/src/share/classes/sun/reflect/misc/ReflectUtil.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/reflect/misc/ReflectUtil.java	Fri Jan 10 15:04:46 2014 +0000
@@ -26,11 +26,13 @@
 
 package sun.reflect.misc;
 
+import java.lang.reflect.Member;
 import java.lang.reflect.Method;
 import java.lang.reflect.Modifier;
 import java.lang.reflect.Proxy;
 import java.util.Arrays;
 import sun.reflect.Reflection;
+import sun.security.util.SecurityConstants;
 
 public final class ReflectUtil {
 
@@ -118,6 +120,40 @@
     }
 
     /**
+     * Does a conservative approximation of member access check. Use this if
+     * you don't have an actual 'userland' caller Class/ClassLoader available.
+     * This might be more restrictive than a precise member access check where
+     * you have a caller, but should never allow a member access that is
+     * forbidden.
+     *
+     * @param m the {@code Member} about to be accessed
+     */
+    public static void conservativeCheckMemberAccess(Member m) throws SecurityException{
+        final SecurityManager sm = System.getSecurityManager();
+        if (sm == null)
+            return;
+
+        // Check for package access on the declaring class.
+        //
+        // In addition, unless the member and the declaring class are both
+        // public check for access declared member permissions.
+        //
+        // This is done regardless of ClassLoader relations between the {@code
+        // Member m} and any potential caller.
+
+        final Class<?> declaringClass = m.getDeclaringClass();
+
+        checkPackageAccess(declaringClass);
+
+        if (Modifier.isPublic(m.getModifiers()) &&
+                Modifier.isPublic(declaringClass.getModifiers()))
+            return;
+
+        // Check for declared member access.
+        sm.checkPermission(SecurityConstants.CHECK_MEMBER_ACCESS_PERMISSION);
+    }
+
+    /**
      * Checks package access on the given class.
      *
      * If it is a {@link Proxy#isProxyClass(java.lang.Class)} that implements
--- a/jdk/src/share/classes/sun/rmi/registry/RegistryImpl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/rmi/registry/RegistryImpl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -94,8 +94,23 @@
                         RMIServerSocketFactory ssf)
         throws RemoteException
     {
-        LiveRef lref = new LiveRef(id, port, csf, ssf);
-        setup(new UnicastServerRef2(lref));
+        if (port == Registry.REGISTRY_PORT && System.getSecurityManager() != null) {
+            // grant permission for default port only.
+            try {
+                AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
+                    public Void run() throws RemoteException {
+                        LiveRef lref = new LiveRef(id, port, csf, ssf);
+                        setup(new UnicastServerRef2(lref));
+                        return null;
+                    }
+                }, null, new SocketPermission("localhost:"+port, "listen,accept"));
+            } catch (PrivilegedActionException pae) {
+                throw (RemoteException)pae.getException();
+            }
+        } else {
+            LiveRef lref = new LiveRef(id, port, csf, ssf);
+            setup(new UnicastServerRef2(lref));
+        }
     }
 
     /**
@@ -104,8 +119,23 @@
     public RegistryImpl(int port)
         throws RemoteException
     {
-        LiveRef lref = new LiveRef(id, port);
-        setup(new UnicastServerRef(lref));
+        if (port == Registry.REGISTRY_PORT && System.getSecurityManager() != null) {
+            // grant permission for default port only.
+            try {
+                AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
+                    public Void run() throws RemoteException {
+                        LiveRef lref = new LiveRef(id, port);
+                        setup(new UnicastServerRef(lref));
+                        return null;
+                    }
+                }, null, new SocketPermission("localhost:"+port, "listen,accept"));
+            } catch (PrivilegedActionException pae) {
+                throw (RemoteException)pae.getException();
+            }
+        } else {
+            LiveRef lref = new LiveRef(id, port);
+            setup(new UnicastServerRef(lref));
+        }
     }
 
     /*
@@ -352,7 +382,7 @@
                         public RegistryImpl run() throws RemoteException {
                             return new RegistryImpl(regPort);
                         }
-                    }, getAccessControlContext());
+                    }, getAccessControlContext(regPort));
             } catch (PrivilegedActionException ex) {
                 throw (RemoteException) ex.getException();
             }
@@ -382,7 +412,7 @@
      * The approach used here is taken from the similar method
      * getAccessControlContext() in the sun.applet.AppletPanel class.
      */
-    private static AccessControlContext getAccessControlContext() {
+    private static AccessControlContext getAccessControlContext(int port) {
         // begin with permissions granted to all code in current policy
         PermissionCollection perms = AccessController.doPrivileged(
             new java.security.PrivilegedAction<PermissionCollection>() {
@@ -404,6 +434,7 @@
          * related classes themselves are more tightly limited by RMI.
          */
         perms.add(new SocketPermission("*", "connect,accept"));
+        perms.add(new SocketPermission("localhost:"+port, "listen,accept"));
 
         perms.add(new RuntimePermission("accessClassInPackage.sun.jvmstat.*"));
         perms.add(new RuntimePermission("accessClassInPackage.sun.jvm.hotspot.*"));
--- a/jdk/src/share/classes/sun/security/internal/spec/TlsRsaPremasterSecretParameterSpec.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/internal/spec/TlsRsaPremasterSecretParameterSpec.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -45,11 +45,12 @@
 
     private final int majorVersion;
     private final int minorVersion;
+    private final byte[] encodedSecret;
 
     /**
      * Constructs a new TlsRsaPremasterSecretParameterSpec.
-     *
-     * <p>The version numbers will be placed inside the premaster secret to
+     * <P>
+     * The version numbers will be placed inside the premaster secret to
      * detect version rollbacks attacks as described in the TLS specification.
      * Note that they do not indicate the protocol version negotiated for
      * the handshake.
@@ -65,7 +66,42 @@
         this.majorVersion =
             TlsMasterSecretParameterSpec.checkVersion(majorVersion);
         this.minorVersion =
-            TlsMasterSecretParameterSpec.checkVersion(minorVersion); }
+            TlsMasterSecretParameterSpec.checkVersion(minorVersion);
+        this.encodedSecret = null;
+    }
+
+    /**
+     * Constructs a new TlsRsaPremasterSecretParameterSpec.
+     * <P>
+     * The version numbers will be placed inside the premaster secret to
+     * detect version rollbacks attacks as described in the TLS specification.
+     * Note that they do not indicate the protocol version negotiated for
+     * the handshake.
+     * <P>
+     * Usually, the encoded secret key is a random number that acts as
+     * dummy pre_master_secret to avoid vulnerabilities described by
+     * section 7.4.7.1, RFC 5246.
+     *
+     * @param majorVersion the major number of the protocol version
+     * @param minorVersion the minor number of the protocol version
+     * @param encodedSecret the encoded secret key
+     *
+     * @throws IllegalArgumentException if minorVersion or majorVersion are
+     *   negative or larger than 255, or encodedSecret is not exactly 48 bytes.
+     */
+    public TlsRsaPremasterSecretParameterSpec(int majorVersion,
+            int minorVersion, byte[] encodedSecret) {
+        this.majorVersion =
+            TlsMasterSecretParameterSpec.checkVersion(majorVersion);
+        this.minorVersion =
+            TlsMasterSecretParameterSpec.checkVersion(minorVersion);
+
+        if (encodedSecret == null || encodedSecret.length != 48) {
+            throw new IllegalArgumentException(
+                        "Encoded secret is not exactly 48 bytes");
+        }
+        this.encodedSecret = encodedSecret.clone();
+    }
 
     /**
      * Returns the major version.
@@ -84,4 +120,13 @@
     public int getMinorVersion() {
         return minorVersion;
     }
+
+    /**
+     * Returns the encoded secret.
+     *
+     * @return the encoded secret, may be null if no encoded secret.
+     */
+    public byte[] getEncodedSecret() {
+        return encodedSecret == null ? null : encodedSecret.clone();
+    }
 }
--- a/jdk/src/share/classes/sun/security/pkcs11/P11RSACipher.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/pkcs11/P11RSACipher.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -451,30 +451,7 @@
     // see JCE spec
     protected Key engineUnwrap(byte[] wrappedKey, String algorithm,
             int type) throws InvalidKeyException, NoSuchAlgorithmException {
-        if (algorithm.equals("TlsRsaPremasterSecret")) {
-            // the instance variable "session" has been initialized for
-            // decrypt mode, so use a local variable instead.
-            Session s = null;
-            try {
-                s = token.getObjSession();
-                long keyType = CKK_GENERIC_SECRET;
-                CK_ATTRIBUTE[] attributes = new CK_ATTRIBUTE[] {
-                    new CK_ATTRIBUTE(CKA_CLASS, CKO_SECRET_KEY),
-                    new CK_ATTRIBUTE(CKA_KEY_TYPE, keyType),
-                };
-                attributes = token.getAttributes
-                    (O_IMPORT, CKO_SECRET_KEY, keyType, attributes);
-                long keyID = token.p11.C_UnwrapKey(s.id(),
-                        new CK_MECHANISM(mechanism), p11Key.keyID, wrappedKey,
-                        attributes);
-                return P11Key.secretKey(s, keyID, algorithm, 48 << 3,
-                        attributes);
-            } catch (PKCS11Exception e) {
-                throw new InvalidKeyException("unwrap() failed", e);
-            } finally {
-                token.releaseSession(s);
-            }
-        }
+
         // XXX implement unwrap using C_Unwrap() for all keys
         implInit(Cipher.DECRYPT_MODE, p11Key);
         if (wrappedKey.length > maxInputSize) {
--- a/jdk/src/share/classes/sun/security/pkcs11/P11TlsRsaPremasterSecretGenerator.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/pkcs11/P11TlsRsaPremasterSecretGenerator.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2005, 2007, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2005, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -88,23 +88,33 @@
             throw new IllegalStateException
                         ("TlsRsaPremasterSecretGenerator must be initialized");
         }
-        CK_VERSION version =
-                new CK_VERSION(spec.getMajorVersion(), spec.getMinorVersion());
-        Session session = null;
-        try {
-            session = token.getObjSession();
-            CK_ATTRIBUTE[] attributes = token.getAttributes
-                (O_GENERATE, CKO_SECRET_KEY, CKK_GENERIC_SECRET, new CK_ATTRIBUTE[0]);
-            long keyID = token.p11.C_GenerateKey
-                (session.id(), new CK_MECHANISM(mechanism, version), attributes);
-            SecretKey key = P11Key.secretKey
-                (session, keyID, "TlsRsaPremasterSecret", 48 << 3, attributes);
-            return key;
-        } catch (PKCS11Exception e) {
-            throw new ProviderException("Could not generate premaster secret", e);
-        } finally {
-            token.releaseSession(session);
+
+        byte[] b = spec.getEncodedSecret();
+        if (b == null) {
+            CK_VERSION version = new CK_VERSION(
+                        spec.getMajorVersion(), spec.getMinorVersion());
+            Session session = null;
+            try {
+                session = token.getObjSession();
+                CK_ATTRIBUTE[] attributes = token.getAttributes(
+                        O_GENERATE, CKO_SECRET_KEY,
+                        CKK_GENERIC_SECRET, new CK_ATTRIBUTE[0]);
+                long keyID = token.p11.C_GenerateKey(session.id(),
+                        new CK_MECHANISM(mechanism, version), attributes);
+                SecretKey key = P11Key.secretKey(session,
+                        keyID, "TlsRsaPremasterSecret", 48 << 3, attributes);
+                return key;
+            } catch (PKCS11Exception e) {
+                throw new ProviderException(
+                        "Could not generate premaster secret", e);
+            } finally {
+                token.releaseSession(session);
+            }
         }
+
+        // Won't worry, the TlsRsaPremasterSecret will be soon converted to
+        // TlsMasterSecret.
+        return new SecretKeySpec(b, "TlsRsaPremasterSecret");
     }
 
 }
--- a/jdk/src/share/classes/sun/security/provider/ByteArrayAccess.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/provider/ByteArrayAccess.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2006, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2006, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -43,10 +43,8 @@
  * These are the only platforms we currently support, but other optimized
  * variants could be added as needed.
  *
- * NOTE that because this code performs unchecked direct memory access, it
- * MUST be restricted to trusted code. It is imperative that the caller protects
- * against out of bounds memory access by performing the necessary bounds
- * checks before calling methods in this class.
+ * NOTE that ArrayIndexOutOfBoundsException will be thrown if the bounds checks
+ * failed.
  *
  * This class may also be helpful in improving the performance of the
  * crypto code in the SunJCE provider. However, for now it is only accessible by
@@ -103,6 +101,10 @@
      * byte[] to int[] conversion, little endian byte order.
      */
     static void b2iLittle(byte[] in, int inOfs, int[] out, int outOfs, int len) {
+        if ((inOfs < 0) || ((in.length - inOfs) < len) ||
+            (outOfs < 0) || ((out.length - outOfs) < len/4)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             inOfs += byteArrayOfs;
             len += inOfs;
@@ -131,6 +133,10 @@
 
     // Special optimization of b2iLittle(in, inOfs, out, 0, 64)
     static void b2iLittle64(byte[] in, int inOfs, int[] out) {
+        if ((inOfs < 0) || ((in.length - inOfs) < 64) ||
+            (out.length < 16)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             inOfs += byteArrayOfs;
             out[ 0] = unsafe.getInt(in, (long)(inOfs     ));
@@ -176,6 +182,10 @@
      * int[] to byte[] conversion, little endian byte order.
      */
     static void i2bLittle(int[] in, int inOfs, byte[] out, int outOfs, int len) {
+        if ((inOfs < 0) || ((in.length - inOfs) < len/4) ||
+            (outOfs < 0) || ((out.length - outOfs) < len)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             outOfs += byteArrayOfs;
             len += outOfs;
@@ -204,6 +214,9 @@
 
     // Store one 32-bit value into out[outOfs..outOfs+3] in little endian order.
     static void i2bLittle4(int val, byte[] out, int outOfs) {
+        if ((outOfs < 0) || ((out.length - outOfs) < 4)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             unsafe.putInt(out, (long)(byteArrayOfs + outOfs), val);
         } else if (bigEndian && ((outOfs & 3) == 0)) {
@@ -220,6 +233,10 @@
      * byte[] to int[] conversion, big endian byte order.
      */
     static void b2iBig(byte[] in, int inOfs, int[] out, int outOfs, int len) {
+        if ((inOfs < 0) || ((in.length - inOfs) < len) ||
+            (outOfs < 0) || ((out.length - outOfs) < len/4)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             inOfs += byteArrayOfs;
             len += inOfs;
@@ -248,6 +265,10 @@
 
     // Special optimization of b2iBig(in, inOfs, out, 0, 64)
     static void b2iBig64(byte[] in, int inOfs, int[] out) {
+        if ((inOfs < 0) || ((in.length - inOfs) < 64) ||
+            (out.length < 16)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             inOfs += byteArrayOfs;
             out[ 0] = reverseBytes(unsafe.getInt(in, (long)(inOfs     )));
@@ -293,6 +314,10 @@
      * int[] to byte[] conversion, big endian byte order.
      */
     static void i2bBig(int[] in, int inOfs, byte[] out, int outOfs, int len) {
+        if ((inOfs < 0) || ((in.length - inOfs) < len/4) ||
+            (outOfs < 0) || ((out.length - outOfs) < len)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             outOfs += byteArrayOfs;
             len += outOfs;
@@ -321,6 +346,9 @@
 
     // Store one 32-bit value into out[outOfs..outOfs+3] in big endian order.
     static void i2bBig4(int val, byte[] out, int outOfs) {
+        if ((outOfs < 0) || ((out.length - outOfs) < 4)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             unsafe.putInt(out, (long)(byteArrayOfs + outOfs), reverseBytes(val));
         } else if (bigEndian && ((outOfs & 3) == 0)) {
@@ -337,6 +365,10 @@
      * byte[] to long[] conversion, big endian byte order.
      */
     static void b2lBig(byte[] in, int inOfs, long[] out, int outOfs, int len) {
+        if ((inOfs < 0) || ((in.length - inOfs) < len) ||
+            (outOfs < 0) || ((out.length - outOfs) < len/8)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             inOfs += byteArrayOfs;
             len += inOfs;
@@ -378,6 +410,10 @@
 
     // Special optimization of b2lBig(in, inOfs, out, 0, 128)
     static void b2lBig128(byte[] in, int inOfs, long[] out) {
+        if ((inOfs < 0) || ((in.length - inOfs) < 128) ||
+            (out.length < 16)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         if (littleEndianUnaligned) {
             inOfs += byteArrayOfs;
             out[ 0] = reverseBytes(unsafe.getLong(in, (long)(inOfs      )));
@@ -406,6 +442,10 @@
      * long[] to byte[] conversion, big endian byte order.
      */
     static void l2bBig(long[] in, int inOfs, byte[] out, int outOfs, int len) {
+        if ((inOfs < 0) || ((in.length - inOfs) < len/8) ||
+            (outOfs < 0) || ((out.length - outOfs) < len)) {
+            throw new ArrayIndexOutOfBoundsException();
+        }
         len += outOfs;
         while (outOfs < len) {
             long i = in[inOfs++];
@@ -419,5 +459,4 @@
             out[outOfs++] = (byte)(i      );
         }
     }
-
 }
--- a/jdk/src/share/classes/sun/security/rsa/RSAPadding.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/rsa/RSAPadding.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2003, 2013 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2003, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -318,33 +318,53 @@
 
     /**
      * PKCS#1 v1.5 unpadding (blocktype 1 and 2).
+     *
+     * Note that we want to make it a constant-time operation
      */
     private byte[] unpadV15(byte[] padded) throws BadPaddingException {
         int k = 0;
+        BadPaddingException bpe = null;
+
         if (padded[k++] != 0) {
-            throw new BadPaddingException("Data must start with zero");
+            bpe = new BadPaddingException("Data must start with zero");
         }
-        if (padded[k++] != type) {
-            throw new BadPaddingException("Blocktype mismatch: " + padded[1]);
+        if (padded[k++] != type && bpe == null) {
+            bpe = new BadPaddingException("Blocktype mismatch: " + padded[1]);
         }
-        while (true) {
+        int p = 0;
+        while (k < padded.length) {
             int b = padded[k++] & 0xff;
-            if (b == 0) {
-                break;
+            if (b == 0 && p == 0) {
+                p = k;
             }
-            if (k == padded.length) {
-                throw new BadPaddingException("Padding string not terminated");
+            if (k == padded.length && p == 0 && bpe == null) {
+                bpe = new BadPaddingException("Padding string not terminated");
             }
-            if ((type == PAD_BLOCKTYPE_1) && (b != 0xff)) {
-                throw new BadPaddingException("Padding byte not 0xff: " + b);
+            if ((type == PAD_BLOCKTYPE_1) && (b != 0xff) &&
+                    p == 0 && bpe == null) {
+                bpe = new BadPaddingException("Padding byte not 0xff: " + b);
             }
         }
-        int n = padded.length - k;
-        if (n > maxDataSize) {
-            throw new BadPaddingException("Padding string too short");
+        int n = padded.length - p;
+        if (n > maxDataSize && bpe == null) {
+            bpe = new BadPaddingException("Padding string too short");
         }
+
+        // copy useless padding array for a constant-time method
+        //
+        // Is it necessary?
+        byte[] padding = new byte[p];
+        System.arraycopy(padded, 0, padding, 0, p);
+
         byte[] data = new byte[n];
-        System.arraycopy(padded, padded.length - n, data, 0, n);
+        System.arraycopy(padded, p, data, 0, n);
+
+        if (bpe == null) {
+            bpe = new BadPaddingException("Unused exception");
+        } else {
+            throw bpe;
+        }
+
         return data;
     }
 
--- a/jdk/src/share/classes/sun/security/ssl/Handshaker.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/ssl/Handshaker.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1104,94 +1104,23 @@
                 clnt_random.random_bytes, svr_random.random_bytes,
                 prfHashAlg, prfHashLength, prfBlockSize);
 
-        SecretKey masterSecret;
         try {
             KeyGenerator kg = JsseJce.getKeyGenerator(masterAlg);
             kg.init(spec);
-            masterSecret = kg.generateKey();
-        } catch (GeneralSecurityException e) {
+            return kg.generateKey();
+        } catch (InvalidAlgorithmParameterException |
+                NoSuchAlgorithmException iae) {
+            // unlikely to happen, otherwise, must be a provider exception
+            //
             // For RSA premaster secrets, do not signal a protocol error
             // due to the Bleichenbacher attack. See comments further down.
-            if (!preMasterSecret.getAlgorithm().equals(
-                    "TlsRsaPremasterSecret")) {
-                throw new ProviderException(e);
-            }
-
             if (debug != null && Debug.isOn("handshake")) {
                 System.out.println("RSA master secret generation error:");
-                e.printStackTrace(System.out);
-            }
-
-            if (requestedVersion != null) {
-                preMasterSecret =
-                    RSAClientKeyExchange.generateDummySecret(requestedVersion);
-            } else {
-                preMasterSecret =
-                    RSAClientKeyExchange.generateDummySecret(protocolVersion);
+                iae.printStackTrace(System.out);
             }
-
-            // recursive call with new premaster secret
-            return calculateMasterSecret(preMasterSecret, null);
-        }
-
-        // if no version check requested (client side handshake), or version
-        // information is not available (not an RSA premaster secret),
-        // return master secret immediately.
-        if ((requestedVersion == null) ||
-                !(masterSecret instanceof TlsMasterSecret)) {
-            return masterSecret;
-        }
-
-        // we have checked the ClientKeyExchange message when reading TLS
-        // record, the following check is necessary to ensure that
-        // JCE provider does not ignore the checking, or the previous
-        // checking process bypassed the premaster secret version checking.
-        TlsMasterSecret tlsKey = (TlsMasterSecret)masterSecret;
-        int major = tlsKey.getMajorVersion();
-        int minor = tlsKey.getMinorVersion();
-        if ((major < 0) || (minor < 0)) {
-            return masterSecret;
-        }
+            throw new ProviderException(iae);
 
-        // check if the premaster secret version is ok
-        // the specification says that it must be the maximum version supported
-        // by the client from its ClientHello message. However, many
-        // implementations send the negotiated version, so accept both
-        // for SSL v3.0 and TLS v1.0.
-        // NOTE that we may be comparing two unsupported version numbers, which
-        // is why we cannot use object reference equality in this special case.
-        ProtocolVersion premasterVersion =
-                                    ProtocolVersion.valueOf(major, minor);
-        boolean versionMismatch = (premasterVersion.v != requestedVersion.v);
-
-        /*
-         * we never checked the client_version in server side
-         * for TLS v1.0 and SSL v3.0. For compatibility, we
-         * maintain this behavior.
-         */
-        if (versionMismatch && requestedVersion.v <= ProtocolVersion.TLS10.v) {
-            versionMismatch = (premasterVersion.v != protocolVersion.v);
         }
-
-        if (versionMismatch == false) {
-            // check passed, return key
-            return masterSecret;
-        }
-
-        // Due to the Bleichenbacher attack, do not signal a protocol error.
-        // Generate a random premaster secret and continue with the handshake,
-        // which will fail when verifying the finished messages.
-        // For more information, see comments in PreMasterSecret.
-        if (debug != null && Debug.isOn("handshake")) {
-            System.out.println("RSA PreMasterSecret version error: expected"
-                + protocolVersion + " or " + requestedVersion + ", decrypted: "
-                + premasterVersion);
-        }
-        preMasterSecret =
-            RSAClientKeyExchange.generateDummySecret(requestedVersion);
-
-        // recursive call with new premaster secret
-        return calculateMasterSecret(preMasterSecret, null);
     }
 
     /*
--- a/jdk/src/share/classes/sun/security/ssl/RSAClientKeyExchange.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/ssl/RSAClientKeyExchange.java	Fri Jan 10 15:04:46 2014 +0000
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2013, Oracle and/or its affiliates. All rights reserved.
  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
  *
  * This code is free software; you can redistribute it and/or modify it
@@ -133,26 +133,37 @@
         } else {
             encrypted = new byte [messageSize];
             if (input.read(encrypted) != messageSize) {
-                throw new SSLProtocolException
-                        ("SSL: read PreMasterSecret: short read");
+                throw new SSLProtocolException(
+                        "SSL: read PreMasterSecret: short read");
             }
         }
 
+        Exception failover = null;
+        byte[] encoded = null;
         try {
             Cipher cipher = JsseJce.getCipher(JsseJce.CIPHER_RSA_PKCS1);
-            cipher.init(Cipher.UNWRAP_MODE, privateKey);
-            preMaster = (SecretKey)cipher.unwrap(encrypted,
-                                "TlsRsaPremasterSecret", Cipher.SECRET_KEY);
+            // Cannot generate key here, please don't use Cipher.UNWRAP_MODE!
+            cipher.init(Cipher.DECRYPT_MODE, privateKey);
+            encoded = cipher.doFinal(encrypted);
+        } catch (BadPaddingException bpe) {
+            failover = bpe;
+            encoded = null;
+        } catch (IllegalBlockSizeException ibse) {
+            // the message it too big to process with RSA
+            throw new SSLProtocolException(
+                "Unable to process PreMasterSecret, may be too big");
+        } catch (Exception e) {
+            // unlikely to happen, otherwise, must be a provider exception
+            if (debug != null && Debug.isOn("handshake")) {
+                System.out.println("RSA premaster secret decryption error:");
+                e.printStackTrace(System.out);
+            }
+            throw new RuntimeException("Could not generate dummy secret", e);
+        }
 
-            // polish the premaster secret
-            preMaster = polishPreMasterSecretKey(currentVersion, maxVersion,
-                                                generator, preMaster, null);
-        } catch (Exception e) {
-            // polish the premaster secret
-            preMaster =
-                    polishPreMasterSecretKey(currentVersion, maxVersion,
-                                                generator, null, e);
-        }
+        // polish the premaster secret
+        preMaster = polishPreMasterSecretKey(
+                    currentVersion, maxVersion, generator, encoded, failover);
     }
 
     /**
@@ -163,85 +174,74 @@
      *
      * RFC 5246 describes the approach as :
      *
-     *  1. Generate a string R of 46 random bytes
+     *  1. Generate a string R of 48 random bytes
      *
      *  2. Decrypt the message to recover the plaintext M
      *
      *  3. If the PKCS#1 padding is not correct, or the length of message
      *     M is not exactly 48 bytes:
-     *        pre_master_secret = ClientHello.client_version || R
+     *        pre_master_secret = R
      *     else If ClientHello.client_version <= TLS 1.0, and version
      *     number check is explicitly disabled:
-     *        pre_master_secret = M
+     *        premaster secret = M
+     *     else If M[0..1] != ClientHello.client_version:
+     *        premaster secret = R
      *     else:
-     *        pre_master_secret = ClientHello.client_version || M[2..47]
+     *        premaster secret = M
+     *
+     * Note that #2 has completed before the call of this method.
      */
     private SecretKey polishPreMasterSecretKey(ProtocolVersion currentVersion,
             ProtocolVersion clientHelloVersion, SecureRandom generator,
-            SecretKey secretKey, Exception failoverException) {
+            byte[] encoded, Exception failoverException) {
 
         this.protocolVersion = clientHelloVersion;
+        if (generator == null) {
+            generator = new SecureRandom();
+        }
+        byte[] random = new byte[48];
+        generator.nextBytes(random);
 
-        if (failoverException == null && secretKey != null) {
+        if (failoverException == null && encoded != null) {
             // check the length
-            byte[] encoded = secretKey.getEncoded();
-            if (encoded == null) {      // unable to get the encoded key
+            if (encoded.length != 48) {
                 if (debug != null && Debug.isOn("handshake")) {
                     System.out.println(
-                        "unable to get the plaintext of the premaster secret");
+                        "incorrect length of premaster secret: " +
+                        encoded.length);
                 }
 
-                int keySize = KeyUtil.getKeySize(secretKey);
-                if (keySize > 0 && keySize != 384) {       // 384 = 48 * 8
-                    if (debug != null && Debug.isOn("handshake")) {
-                        System.out.println(
-                            "incorrect length of premaster secret: " +
-                            (keySize/8));
-                    }
-
-                    return generateDummySecret(clientHelloVersion);
-                }
+                return generatePreMasterSecret(
+                        clientHelloVersion, random, generator);
+            }
 
-                // The key size is exactly 48 bytes or not accessible.
-                //
-                // Conservatively, pass the checking to master secret
-                // calculation.
-                return secretKey;
-            } else if (encoded.length == 48) {
-                // check the version
-                if (clientHelloVersion.major == encoded[0] &&
-                    clientHelloVersion.minor == encoded[1]) {
+            if (clientHelloVersion.major != encoded[0] ||
+                        clientHelloVersion.minor != encoded[1]) {
 
-                    return secretKey;
-                } else if (clientHelloVersion.v <= ProtocolVersion.TLS10.v &&
-                           currentVersion.major == encoded[0] &&
-                           currentVersion.minor == encoded[1]) {
+                if (clientHelloVersion.v <= ProtocolVersion.TLS10.v &&
+                       currentVersion.major == encoded[0] &&
+                       currentVersion.minor == encoded[1]) {
                     /*
                      * For compatibility, we maintain the behavior that the
                      * version in pre_master_secret can be the negotiated
                      * version for TLS v1.0 and SSL v3.0.
                      */
                     this.protocolVersion = currentVersion;
-                    return secretKey;
-                }
-
-                if (debug != null && Debug.isOn("handshake")) {
-                    System.out.println("Mismatching Protocol Versions, " +
-                        "ClientHello.client_version is " + clientHelloVersion +
-                        ", while PreMasterSecret.client_version is " +
-                        ProtocolVersion.valueOf(encoded[0], encoded[1]));
-                }
+                } else {
+                    if (debug != null && Debug.isOn("handshake")) {
+                        System.out.println("Mismatching Protocol Versions, " +
+                            "ClientHello.client_version is " +
+                            clientHelloVersion +
+                            ", while PreMasterSecret.client_version is " +
+                            ProtocolVersion.valueOf(encoded[0], encoded[1]));
+                    }
 
-                return generateDummySecret(clientHelloVersion);
-            } else {
-                if (debug != null && Debug.isOn("handshake")) {
-                    System.out.println(
-                        "incorrect length of premaster secret: " +
-                        encoded.length);
+                    encoded = random;
                 }
+            }
 
-                return generateDummySecret(clientHelloVersion);
-            }
+            return generatePreMasterSecret(
+                    clientHelloVersion, encoded, generator);
         }
 
         if (debug != null && Debug.isOn("handshake") &&
@@ -250,11 +250,14 @@
             failoverException.printStackTrace(System.out);
         }
 
-        return generateDummySecret(clientHelloVersion);
+        return generatePreMasterSecret(clientHelloVersion, random, generator);
     }
 
     // generate a premaster secret with the specified version number
-    static SecretKey generateDummySecret(ProtocolVersion version) {
+    private static SecretKey generatePreMasterSecret(
+            ProtocolVersion version, byte[] encodedSecret,
+            SecureRandom generator) {
+
         if (debug != null && Debug.isOn("handshake")) {
             System.out.println("Generating a random fake premaster secret");
         }
@@ -263,11 +266,17 @@
             String s = ((version.v >= ProtocolVersion.TLS12.v) ?
                 "SunTls12RsaPremasterSecret" : "SunTlsRsaPremasterSecret");
             KeyGenerator kg = JsseJce.getKeyGenerator(s);
-            kg.init(new TlsRsaPremasterSecretParameterSpec
-                    (version.major, version.minor));
+            kg.init(new TlsRsaPremasterSecretParameterSpec(
+                    version.major, version.minor, encodedSecret), generator);
             return kg.generateKey();
-        } catch (GeneralSecurityException e) {
-            throw new RuntimeException("Could not generate dummy secret", e);
+        } catch (InvalidAlgorithmParameterException |
+                NoSuchAlgorithmException iae) {
+            // unlikely to happen, otherwise, must be a provider exception
+            if (debug != null && Debug.isOn("handshake")) {
+                System.out.println("RSA premaster secret generation error:");
+                iae.printStackTrace(System.out);
+            }
+            throw new RuntimeException("Could not generate dummy secret", iae);
         }
     }
 
--- a/jdk/src/share/classes/sun/security/tools/jarsigner/Main.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/tools/jarsigner/Main.java	Fri Jan 10 15:04:46 2014 +0000
@@ -158,8 +158,13 @@
     private String altSignerClasspath = null;
     private ZipFile zipFile = null;
 
+    // Informational warnings
+    private boolean hasExpiringCert = false;
+    private boolean noTimestamp = false;
+    private Date expireDate = new Date(0L);     // used in noTimestamp warning
+
+    // Severe warnings
     private boolean hasExpiredCert = false;
-    private boolean hasExpiringCert = false;
     private boolean notYetValidCert = false;
     private boolean chainNotValidated = false;
     private boolean notSignedByAlias = false;
@@ -258,9 +263,6 @@
 
         if (strict) {
             int exitCode = 0;
-            if (hasExpiringCert) {
-                exitCode |= 2;
-            }
             if (chainNotValidated || hasExpiredCert || notYetValidCert) {
                 exitCode |= 4;
             }
@@ -754,14 +756,25 @@
                 System.out.println(rb.getString(
                       "jar.is.unsigned.signatures.missing.or.not.parsable."));
             } else {
-                System.out.println(rb.getString("jar.verified."));
-                if (hasUnsignedEntry || hasExpiredCert || hasExpiringCert ||
-                    badKeyUsage || badExtendedKeyUsage || badNetscapeCertType ||
-                    notYetValidCert || chainNotValidated ||
-                    aliasNotInStore || notSignedByAlias) {
+                boolean warningAppeared = false;
+                boolean errorAppeared = false;
+                if (badKeyUsage || badExtendedKeyUsage || badNetscapeCertType ||
+                        notYetValidCert || chainNotValidated || hasExpiredCert ||
+                        hasUnsignedEntry ||
+                        aliasNotInStore || notSignedByAlias) {
 
-                    System.out.println();
-                    System.out.println(rb.getString("Warning."));
+                    if (strict) {
+                        System.out.println(rb.getString("jar.verified.with.signer.errors."));
+                        System.out.println();
+                        System.out.println(rb.getString("Error."));
+                        errorAppeared = true;
+                    } else {
+                        System.out.println(rb.getString("jar.verified."));
+                        System.out.println();
+                        System.out.println(rb.getString("Warning."));
+                        warningAppeared = true;
+                    }
+
                     if (badKeyUsage) {
                         System.out.println(
                             rb.getString("This.jar.contains.entries.whose.signer.certificate.s.KeyUsage.extension.doesn.t.allow.code.signing."));
@@ -785,10 +798,6 @@
                         System.out.println(rb.getString(
                             "This.jar.contains.entries.whose.signer.certificate.has.expired."));
                     }
-                    if (hasExpiringCert) {
-                        System.out.println(rb.getString(
-                            "This.jar.contains.entries.whose.signer.certificate.will.expire.within.six.months."));
-                    }
                     if (notYetValidCert) {
                         System.out.println(rb.getString(
                             "This.jar.contains.entries.whose.signer.certificate.is.not.yet.valid."));
@@ -807,10 +816,29 @@
                     if (aliasNotInStore) {
                         System.out.println(rb.getString("This.jar.contains.signed.entries.that.s.not.signed.by.alias.in.this.keystore."));
                     }
+                } else {
+                    System.out.println(rb.getString("jar.verified."));
+                }
+                if (hasExpiringCert || noTimestamp) {
+                    if (!warningAppeared) {
+                        System.out.println();
+                        System.out.println(rb.getString("Warning."));
+                        warningAppeared = true;
+                    }
+                    if (hasExpiringCert) {
+                        System.out.println(rb.getString(
+                                "This.jar.contains.entries.whose.signer.certificate.will.expire.within.six.months."));
+                    }
+                    if (noTimestamp) {
+                        System.out.println(
+                                String.format(rb.getString("no.timestamp.verifying"), expireDate));
+                    }
+                }
+                if (warningAppeared || errorAppeared) {
                     if (! (verbose != null && showcerts)) {
                         System.out.println();
                         System.out.println(rb.getString(
-                            "Re.run.with.the.verbose.and.certs.options.for.more.details."));
+                                "Re.run.with.the.verbose.and.certs.options.for.more.details."));
                     }
                 }
             }
@@ -870,6 +898,9 @@
             try {
                 boolean printValidity = true;
                 if (timestamp == null) {
+                    if (expireDate.getTime() == 0 || expireDate.after(notAfter)) {
+                        expireDate = notAfter;
+                    }
                     x509Cert.checkValidity();
                     // test if cert will expire within six months
                     if (notAfter.getTime() < System.currentTimeMillis() + SIX_MONTHS) {
@@ -1233,6 +1264,10 @@
                 tsaCert = getTsaCert(tsaAlias);
             }
 
+            if (tsaUrl == null && tsaCert == null) {
+                noTimestamp = true;
+            }
+
             SignatureFile.Block block = null;
 
             try {
@@ -1380,12 +1415,20 @@
                 }
             }
 
-            if (hasExpiredCert || hasExpiringCert || notYetValidCert
-                    || badKeyUsage || badExtendedKeyUsage
-                    || badNetscapeCertType || chainNotValidated) {
-                System.out.println();
+            boolean warningAppeared = false;
+            if (badKeyUsage || badExtendedKeyUsage || badNetscapeCertType ||
+                    notYetValidCert || chainNotValidated || hasExpiredCert) {
+                if (strict) {
+                    System.out.println(rb.getString("jar.signed.with.signer.errors."));
+                    System.out.println();
+                    System.out.println(rb.getString("Error."));
+                } else {
+                    System.out.println(rb.getString("jar.signed."));
+                    System.out.println();
+                    System.out.println(rb.getString("Warning."));
+                    warningAppeared = true;
+                }
 
-                System.out.println(rb.getString("Warning."));
                 if (badKeyUsage) {
                     System.out.println(
                         rb.getString("The.signer.certificate.s.KeyUsage.extension.doesn.t.allow.code.signing."));
@@ -1404,9 +1447,6 @@
                 if (hasExpiredCert) {
                     System.out.println(
                         rb.getString("The.signer.certificate.has.expired."));
-                } else if (hasExpiringCert) {
-                    System.out.println(
-                        rb.getString("The.signer.certificate.will.expire.within.six.months."));
                 } else if (notYetValidCert) {
                     System.out.println(
                         rb.getString("The.signer.certificate.is.not.yet.valid."));
@@ -1416,6 +1456,24 @@
                     System.out.println(
                             rb.getString("The.signer.s.certificate.chain.is.not.validated."));
                 }
+            } else {
+                System.out.println(rb.getString("jar.signed."));
+            }
+            if (hasExpiringCert || noTimestamp) {
+                if (!warningAppeared) {
+                    System.out.println();
+                    System.out.println(rb.getString("Warning."));
+                }
+
+                if (hasExpiringCert) {
+                    System.out.println(
+                            rb.getString("The.signer.certificate.will.expire.within.six.months."));
+                }
+
+                if (noTimestamp) {
+                    System.out.println(
+                            String.format(rb.getString("no.timestamp.signing"), expireDate));
+                }
             }
 
         // no IOException thrown in the above try clause, so disable
@@ -1502,6 +1560,7 @@
             timestamp = ts.getTimestamp();
         } else {
             timestamp = null;
+            noTimestamp = true;
         }
         // display the certificate(s). The first one is end-entity cert and
         // its KeyUsage should be checked.
--- a/jdk/src/share/classes/sun/security/tools/jarsigner/Resources.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/tools/jarsigner/Resources.java	Fri Jan 10 15:04:46 2014 +0000
@@ -112,9 +112,9 @@
         {"Please.specify.alias.name", "Please specify alias name"},
         {"Only.one.alias.can.be.specified", "Only one alias can be specified"},
         {"This.jar.contains.signed.entries.which.is.not.signed.by.the.specified.alias.es.",
-                 "This jar contains signed entries which is not signed by the specified alias(es)."},
+                 "This jar contains signed entries which are not signed by the specified alias(es)."},
         {"This.jar.contains.signed.entries.that.s.not.signed.by.alias.in.this.keystore.",
-                  "This jar contains signed entries that's not signed by alias in this keystore."},
+                  "This jar contains signed entries that are not signed by alias in this keystore."},
         {"s", "s"},
         {"m", "m"},
         {"k", "k"},
@@ -135,7 +135,10 @@
         {".Unsigned.entries.", "(Unsigned entries)"},
         {"jar.is.unsigned.signatures.missing.or.not.parsable.",
                 "jar is unsigned. (signatures missing or not parsable)"},
+        {"jar.signed.", "jar signed."},
+        {"jar.signed.with.signer.errors.", "jar signed, with signer errors."},
         {"jar.verified.", "jar verified."},
+        {"jar.verified.with.signer.errors.", "jar verified, with signer errors."},
         {"jarsigner.", "jarsigner: "},
         {"signature.filename.must.consist.of.the.following.characters.A.Z.0.9.or.",
                 "signature filename must consist of the following characters: A-Z, 0-9, _ or -"},
@@ -193,6 +196,7 @@
                 "using an alternative signing mechanism"},
         {"entry.was.signed.on", "entry was signed on {0}"},
         {"Warning.", "Warning: "},
+        {"Error.", "Error: "},
         {"This.jar.contains.unsigned.entries.which.have.not.been.integrity.checked.",
                 "This jar contains unsigned entries which have not been integrity-checked. "},
         {"This.jar.contains.entries.whose.signer.certificate.has.expired.",
@@ -229,6 +233,10 @@
                 "The signer's certificate chain is not validated."},
         {"This.jar.contains.entries.whose.certificate.chain.is.not.validated.",
                  "This jar contains entries whose certificate chain is not validated."},
+        {"no.timestamp.signing",
+                "No -tsa or -tsacert is provided and this jar is not timestamped. Without a timestamp, users may not be able to validate this jar after the signer certificate's expiration date (%1$tY-%1$tm-%1$td) or after any future revocation date."},
+        {"no.timestamp.verifying",
+                "This jar contains signatures that does not include a timestamp. Without a timestamp, users may not be able to validate this jar after the signer certificate's expiration date (%1$tY-%1$tm-%1$td) or after any future revocation date."},
         {"Unknown.password.type.", "Unknown password type: "},
         {"Cannot.find.environment.variable.",
                 "Cannot find environment variable: "},
--- a/jdk/src/share/classes/sun/security/util/SecurityConstants.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/classes/sun/security/util/SecurityConstants.java	Fri Jan 10 15:04:46 2014 +0000
@@ -144,5 +144,5 @@
 
     // java.lang.SecurityManager
     public static final SocketPermission LOCAL_LISTEN_PERMISSION =
-        new SocketPermission("localhost:1024-", SOCKET_LISTEN_ACTION);
+        new SocketPermission("localhost:0", SOCKET_LISTEN_ACTION);
 }
--- a/jdk/src/share/lib/security/java.policy	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/lib/security/java.policy	Fri Jan 10 15:04:46 2014 +0000
@@ -2,48 +2,48 @@
 // Standard extensions get all permissions by default
 
 grant codeBase "file:${{java.ext.dirs}}/*" {
-	permission java.security.AllPermission;
+        permission java.security.AllPermission;
 };
 
 // default permissions granted to all domains
 
-grant { 
-	// Allows any thread to stop itself using the java.lang.Thread.stop()
-	// method that takes no argument.
-	// Note that this permission is granted by default only to remain
-	// backwards compatible.
-	// It is strongly recommended that you either remove this permission
-	// from this policy file or further restrict it to code sources
-	// that you specify, because Thread.stop() is potentially unsafe.
-	// See the API specification of java.lang.Thread.stop() for more 
+grant {
+        // Allows any thread to stop itself using the java.lang.Thread.stop()
+        // method that takes no argument.
+        // Note that this permission is granted by default only to remain
+        // backwards compatible.
+        // It is strongly recommended that you either remove this permission
+        // from this policy file or further restrict it to code sources
+        // that you specify, because Thread.stop() is potentially unsafe.
+        // See the API specification of java.lang.Thread.stop() for more
         // information.
-	permission java.lang.RuntimePermission "stopThread";
+        permission java.lang.RuntimePermission "stopThread";
 
-	// allows anyone to listen on un-privileged ports
-	permission java.net.SocketPermission "localhost:1024-", "listen";
+        // allows anyone to listen on dynamic ports
+        permission java.net.SocketPermission "localhost:0", "listen";
 
-	// "standard" properies that can be read by anyone
+        // "standard" properies that can be read by anyone
 
-	permission java.util.PropertyPermission "java.version", "read";
-	permission java.util.PropertyPermission "java.vendor", "read";
-	permission java.util.PropertyPermission "java.vendor.url", "read";
-	permission java.util.PropertyPermission "java.class.version", "read";
-	permission java.util.PropertyPermission "os.name", "read";
-	permission java.util.PropertyPermission "os.version", "read";
-	permission java.util.PropertyPermission "os.arch", "read";
-	permission java.util.PropertyPermission "file.separator", "read";
-	permission java.util.PropertyPermission "path.separator", "read";
-	permission java.util.PropertyPermission "line.separator", "read";
+        permission java.util.PropertyPermission "java.version", "read";
+        permission java.util.PropertyPermission "java.vendor", "read";
+        permission java.util.PropertyPermission "java.vendor.url", "read";
+        permission java.util.PropertyPermission "java.class.version", "read";
+        permission java.util.PropertyPermission "os.name", "read";
+        permission java.util.PropertyPermission "os.version", "read";
+        permission java.util.PropertyPermission "os.arch", "read";
+        permission java.util.PropertyPermission "file.separator", "read";
+        permission java.util.PropertyPermission "path.separator", "read";
+        permission java.util.PropertyPermission "line.separator", "read";
 
-	permission java.util.PropertyPermission "java.specification.version", "read";
-	permission java.util.PropertyPermission "java.specification.vendor", "read";
-	permission java.util.PropertyPermission "java.specification.name", "read";
+        permission java.util.PropertyPermission "java.specification.version", "read";
+        permission java.util.PropertyPermission "java.specification.vendor", "read";
+        permission java.util.PropertyPermission "java.specification.name", "read";
 
-	permission java.util.PropertyPermission "java.vm.specification.version", "read";
-	permission java.util.PropertyPermission "java.vm.specification.vendor", "read";
-	permission java.util.PropertyPermission "java.vm.specification.name", "read";
-	permission java.util.PropertyPermission "java.vm.version", "read";
-	permission java.util.PropertyPermission "java.vm.vendor", "read";
-	permission java.util.PropertyPermission "java.vm.name", "read";
+        permission java.util.PropertyPermission "java.vm.specification.version", "read";
+        permission java.util.PropertyPermission "java.vm.specification.vendor", "read";
+        permission java.util.PropertyPermission "java.vm.specification.name", "read";
+        permission java.util.PropertyPermission "java.vm.version", "read";
+        permission java.util.PropertyPermission "java.vm.vendor", "read";
+        permission java.util.PropertyPermission "java.vm.name", "read";
 };
 
--- a/jdk/src/share/lib/security/java.security-linux	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/lib/security/java.security-linux	Fri Jan 10 15:04:46 2014 +0000
@@ -182,6 +182,7 @@
                com.sun.istack.internal.,\
                com.sun.jmx.,\
                com.sun.media.sound.,\
+               com.sun.naming.internal.,\
                com.sun.proxy.,\
                com.sun.corba.se.,\
                com.sun.org.apache.bcel.internal.,\
@@ -205,7 +206,7 @@
                com.sun.org.glassfish.,\
                com.oracle.xmlns.internal.,\
                com.oracle.webservices.internal.,\
-	       oracle.jrockit.jfr.,\
+               oracle.jrockit.jfr.,\
                org.jcp.xml.dsig.internal.,\
                jdk.internal.,\
                jdk.nashorn.internal.,\
@@ -228,6 +229,7 @@
                    com.sun.istack.internal.,\
                    com.sun.jmx.,\
                    com.sun.media.sound.,\
+                   com.sun.naming.internal.,\
                    com.sun.proxy.,\
                    com.sun.corba.se.,\
                    com.sun.org.apache.bcel.internal.,\
@@ -251,7 +253,7 @@
                    com.sun.org.glassfish.,\
                    com.oracle.xmlns.internal.,\
                    com.oracle.webservices.internal.,\
-		   oracle.jrockit.jfr.,\
+                   oracle.jrockit.jfr.,\
                    org.jcp.xml.dsig.internal.,\
                    jdk.internal.,\
                    jdk.nashorn.internal.,\
@@ -494,4 +496,3 @@
 #
 # Example:
 #   jdk.tls.disabledAlgorithms=MD5, SHA1, DSA, RSA keySize < 2048
-
--- a/jdk/src/share/lib/security/java.security-macosx	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/lib/security/java.security-macosx	Fri Jan 10 15:04:46 2014 +0000
@@ -183,6 +183,7 @@
                com.sun.istack.internal.,\
                com.sun.jmx.,\
                com.sun.media.sound.,\
+               com.sun.naming.internal.,\
                com.sun.proxy.,\
                com.sun.corba.se.,\
                com.sun.org.apache.bcel.internal.,\
@@ -229,6 +230,7 @@
                    com.sun.istack.internal.,\
                    com.sun.jmx.,\
                    com.sun.media.sound.,\
+                   com.sun.naming.internal.,\
                    com.sun.proxy.,\
                    com.sun.corba.se.,\
                    com.sun.org.apache.bcel.internal.,\
@@ -495,4 +497,3 @@
 #
 # Example:
 #   jdk.tls.disabledAlgorithms=MD5, SHA1, DSA, RSA keySize < 2048
-
--- a/jdk/src/share/lib/security/java.security-solaris	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/lib/security/java.security-solaris	Fri Jan 10 15:04:46 2014 +0000
@@ -184,6 +184,7 @@
                com.sun.istack.internal.,\
                com.sun.jmx.,\
                com.sun.media.sound.,\
+               com.sun.naming.internal.,\
                com.sun.proxy.,\
                com.sun.corba.se.,\
                com.sun.org.apache.bcel.internal.,\
@@ -207,7 +208,7 @@
                com.sun.org.glassfish.,\
                com.oracle.xmlns.internal.,\
                com.oracle.webservices.internal.,\
-	       oracle.jrockit.jfr.,\
+               oracle.jrockit.jfr.,\
                org.jcp.xml.dsig.internal.,\
                jdk.internal.,\
                jdk.nashorn.internal.,\
@@ -229,6 +230,7 @@
                    com.sun.istack.internal.,\
                    com.sun.jmx.,\
                    com.sun.media.sound.,\
+                   com.sun.naming.internal.,\
                    com.sun.proxy.,\
                    com.sun.corba.se.,\
                    com.sun.org.apache.bcel.internal.,\
@@ -252,7 +254,7 @@
                    com.sun.org.glassfish.,\
                    com.oracle.xmlns.internal.,\
                    com.oracle.webservices.internal.,\
-		   oracle.jrockit.jfr.,\
+                   oracle.jrockit.jfr.,\
                    org.jcp.xml.dsig.internal.,\
                    jdk.internal.,\
                    jdk.nashorn.internal.,\
@@ -494,4 +496,3 @@
 #
 # Example:
 #   jdk.tls.disabledAlgorithms=MD5, SHA1, DSA, RSA keySize < 2048
-
--- a/jdk/src/share/lib/security/java.security-windows	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/lib/security/java.security-windows	Fri Jan 10 15:04:46 2014 +0000
@@ -183,6 +183,7 @@
                com.sun.istack.internal.,\
                com.sun.jmx.,\
                com.sun.media.sound.,\
+               com.sun.naming.internal.,\
                com.sun.proxy.,\
                com.sun.corba.se.,\
                com.sun.org.apache.bcel.internal.,\
@@ -206,7 +207,7 @@
                com.sun.org.glassfish.,\
                com.oracle.xmlns.internal.,\
                com.oracle.webservices.internal.,\
-	       oracle.jrockit.jfr.,\
+               oracle.jrockit.jfr.,\
                org.jcp.xml.dsig.internal.,\
                jdk.internal.,\
                jdk.nashorn.internal.,\
@@ -229,6 +230,7 @@
                    com.sun.istack.internal.,\
                    com.sun.jmx.,\
                    com.sun.media.sound.,\
+                   com.sun.naming.internal.,\
                    com.sun.proxy.,\
                    com.sun.corba.se.,\
                    com.sun.org.apache.bcel.internal.,\
@@ -252,7 +254,7 @@
                    com.sun.org.glassfish.,\
                    com.oracle.xmlns.internal.,\
                    com.oracle.webservices.internal.,\
-		   oracle.jrockit.jfr.,\
+                   oracle.jrockit.jfr.,\
                    org.jcp.xml.dsig.internal.,\
                    jdk.internal.,\
                    jdk.nashorn.internal.,\
@@ -495,4 +497,3 @@
 #
 # Example:
 #   jdk.tls.disabledAlgorithms=MD5, SHA1, DSA, RSA keySize < 2048
-
--- a/jdk/src/share/native/sun/awt/splashscreen/splashscreen_impl.c	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/awt/splashscreen/splashscreen_impl.c	Fri Jan 10 15:04:46 2014 +0000
@@ -111,8 +111,9 @@
 int
 SplashIsStillLooping(Splash * splash)
 {
-    if (splash->currentFrame < 0)
+    if (splash->currentFrame < 0) {
         return 0;
+    }
     return splash->loopCount != 1 ||
         splash->currentFrame + 1 < splash->frameCount;
 }
@@ -121,17 +122,22 @@
 SplashUpdateScreenData(Splash * splash)
 {
     ImageRect srcRect, dstRect;
+    if (splash->currentFrame < 0) {
+        return;
+    }
 
     initRect(&srcRect, 0, 0, splash->width, splash->height, 1,
         splash->width * sizeof(rgbquad_t),
         splash->frames[splash->currentFrame].bitmapBits, &splash->imageFormat);
-    if (splash->screenData)
+    if (splash->screenData) {
         free(splash->screenData);
+    }
     splash->screenStride = splash->width * splash->screenFormat.depthBytes;
-    if (splash->byteAlignment > 1)
+    if (splash->byteAlignment > 1) {
         splash->screenStride =
             (splash->screenStride + splash->byteAlignment - 1) &
             ~(splash->byteAlignment - 1);
+    }
     splash->screenData = malloc(splash->height * splash->screenStride);
     initRect(&dstRect, 0, 0, splash->width, splash->height, 1,
         splash->screenStride, splash->screenData, &splash->screenFormat);
@@ -146,16 +152,19 @@
 void
 SplashNextFrame(Splash * splash)
 {
-    if (splash->currentFrame < 0)
+    if (splash->currentFrame < 0) {
         return;
+    }
     do {
-        if (!SplashIsStillLooping(splash))
+        if (!SplashIsStillLooping(splash)) {
             return;
+        }
         splash->time += splash->frames[splash->currentFrame].delay;
         if (++splash->currentFrame >= splash->frameCount) {
             splash->currentFrame = 0;
-            if (splash->loopCount > 0)
+            if (splash->loopCount > 0) {
                 splash->loopCount--;
+            }
         }
     } while (splash->time + splash->frames[splash->currentFrame].delay -
         SplashTime() <= 0);
@@ -183,8 +192,9 @@
                 pSrc += pSrcRect->depthBytes;
                 ++i;
             }
-            if (i >= pSrcRect->numSamples)
+            if (i >= pSrcRect->numSamples) {
                 break;
+            }
             i0 = i;
             while (i < pSrcRect->numSamples &&
                    getRGBA(pSrc, pSrcRect->format) >= ALPHA_THRESHOLD) {
--- a/jdk/src/share/native/sun/font/layout/AlternateSubstSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/AlternateSubstSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -55,7 +55,7 @@
                                   (const AlternateSetTable *) ((char *) this + alternateSetTableOffset));
             TTGlyphID alternate = SWAPW(alternateSetTable->alternateArray[0]);
 
-            if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, alternate))) {
+            if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, alternate), success)) {
                 glyphIterator->setCurrGlyphID(SWAPW(alternateSetTable->alternateArray[0]));
             }
 
--- a/jdk/src/share/native/sun/font/layout/AnchorTables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/AnchorTables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -37,55 +37,54 @@
 
 U_NAMESPACE_BEGIN
 
-void AnchorTable::getAnchor(LEGlyphID glyphID, const LEFontInstance *fontInstance,
-                            LEPoint &anchor) const
+void AnchorTable::getAnchor(const LETableReference &base, LEGlyphID glyphID, const LEFontInstance *fontInstance,
+                            LEPoint &anchor, LEErrorCode &success) const
 {
-    switch(SWAPW(anchorFormat)) {
+  switch(SWAPW(anchorFormat)) {
     case 1:
     {
-        const Format1AnchorTable *f1 = (const Format1AnchorTable *) this;
-
-        f1->getAnchor(fontInstance, anchor);
+        LEReferenceTo<Format1AnchorTable> f1(base, success);
+        f1->getAnchor(f1, fontInstance, anchor, success);
         break;
     }
 
     case 2:
     {
-        const Format2AnchorTable *f2 = (const Format2AnchorTable *) this;
-
-        f2->getAnchor(glyphID, fontInstance, anchor);
+        LEReferenceTo<Format2AnchorTable> f2(base, success);
+        f2->getAnchor(f2, glyphID, fontInstance, anchor, success);
         break;
     }
 
     case 3:
     {
-        const Format3AnchorTable *f3 = (const Format3AnchorTable *) this;
-
-        f3->getAnchor(fontInstance, anchor);
+        LEReferenceTo<Format3AnchorTable> f3(base, success);
+        f3->getAnchor(f3, fontInstance, anchor, success);
         break;
     }
 
     default:
+    {
         // unknown format: just use x, y coordinate, like format 1...
-        const Format1AnchorTable *f1 = (const Format1AnchorTable *) this;
-
-        f1->getAnchor(fontInstance, anchor);
+        LEReferenceTo<Format1AnchorTable> f1(base, success);
+        f1->getAnchor(f1, fontInstance, anchor, success);
         break;
     }
+  }
 }
 
-void Format1AnchorTable::getAnchor(const LEFontInstance *fontInstance, LEPoint &anchor) const
+void Format1AnchorTable::getAnchor(const LEReferenceTo<Format1AnchorTable>& base, const LEFontInstance *fontInstance, LEPoint &anchor, LEErrorCode &success) const
 {
     le_int16 x = SWAPW(xCoordinate);
     le_int16 y = SWAPW(yCoordinate);
     LEPoint pixels;
 
     fontInstance->transformFunits(x, y, pixels);
-
     fontInstance->pixelsToUnits(pixels, anchor);
 }
 
-void Format2AnchorTable::getAnchor(LEGlyphID glyphID, const LEFontInstance *fontInstance, LEPoint &anchor) const
+void Format2AnchorTable::getAnchor(const LEReferenceTo<Format2AnchorTable>& base,
+                                   LEGlyphID glyphID, const LEFontInstance *fontInstance, LEPoint &anchor
+                                   , LEErrorCode &success) const
 {
     LEPoint point;
 
@@ -100,7 +99,8 @@
     fontInstance->pixelsToUnits(point, anchor);
 }
 
-void Format3AnchorTable::getAnchor(const LEFontInstance *fontInstance, LEPoint &anchor) const
+void Format3AnchorTable::getAnchor(const LEReferenceTo<Format3AnchorTable> &base, const LEFontInstance *fontInstance,
+                                   LEPoint &anchor, LEErrorCode &success) const
 {
     le_int16 x = SWAPW(xCoordinate);
     le_int16 y = SWAPW(yCoordinate);
@@ -111,15 +111,15 @@
     fontInstance->transformFunits(x, y, pixels);
 
     if (dtxOffset != 0) {
-        const DeviceTable *dtx = (const DeviceTable *) ((char *) this + dtxOffset);
-        le_int16 adjx = dtx->getAdjustment((le_int16) fontInstance->getXPixelsPerEm());
+        LEReferenceTo<DeviceTable> dt(base, success, dtxOffset);
+        le_int16 adjx = dt->getAdjustment(dt, (le_int16) fontInstance->getXPixelsPerEm(), success);
 
         pixels.fX += adjx;
     }
 
     if (dtyOffset != 0) {
-        const DeviceTable *dty = (const DeviceTable *) ((char *) this + dtyOffset);
-        le_int16 adjy = dty->getAdjustment((le_int16) fontInstance->getYPixelsPerEm());
+        LEReferenceTo<DeviceTable> dt(base, success, dtyOffset);
+        le_int16 adjy = dt->getAdjustment(dt, (le_int16) fontInstance->getYPixelsPerEm(), success);
 
         pixels.fY += adjy;
     }
--- a/jdk/src/share/native/sun/font/layout/AnchorTables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/AnchorTables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -49,20 +49,23 @@
     le_int16   xCoordinate;
     le_int16   yCoordinate;
 
-    void    getAnchor(LEGlyphID glyphID, const LEFontInstance *fontInstance,
-                      LEPoint &anchor) const;
+  void    getAnchor(const LETableReference &base, LEGlyphID glyphID, const LEFontInstance *fontInstance,
+                      LEPoint &anchor, LEErrorCode &success) const;
 };
 
 struct Format1AnchorTable : AnchorTable
 {
-    void getAnchor(const LEFontInstance *fontInstance, LEPoint &anchor) const;
+  void getAnchor(const LEReferenceTo<Format1AnchorTable>& base,
+                 const LEFontInstance *fontInstance, LEPoint &anchor, LEErrorCode &success) const;
 };
 
 struct Format2AnchorTable : AnchorTable
 {
     le_uint16  anchorPoint;
 
-    void getAnchor(LEGlyphID glyphID, const LEFontInstance *fontInstance, LEPoint &anchor) const;
+    void getAnchor(const LEReferenceTo<Format2AnchorTable>& base,
+                   LEGlyphID glyphID, const LEFontInstance *fontInstance,
+                   LEPoint &anchor, LEErrorCode &success) const;
 };
 
 struct Format3AnchorTable : AnchorTable
@@ -70,7 +73,9 @@
     Offset  xDeviceTableOffset;
     Offset  yDeviceTableOffset;
 
-    void getAnchor(const LEFontInstance *fontInstance, LEPoint &anchor) const;
+    void getAnchor(const LEReferenceTo<Format3AnchorTable>& base,
+                   const LEFontInstance *fontInstance, LEPoint &anchor,
+                   LEErrorCode &success) const;
 };
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/ArabicLayoutEngine.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ArabicLayoutEngine.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -51,7 +51,7 @@
 
 U_NAMESPACE_BEGIN
 
-le_bool CharSubstitutionFilter::accept(LEGlyphID glyph) const
+le_bool CharSubstitutionFilter::accept(LEGlyphID glyph, LEErrorCode &/*success*/) const
 {
     return fFontInstance->canDisplay((LEUnicode) glyph);
 }
@@ -147,7 +147,9 @@
         GDEFMarkFilter filter(fGDEFTable, success);
         adjustMarkGlyphs(glyphStorage, &filter, success);
     } else {
-        LEReferenceTo<GlyphDefinitionTableHeader> gdefTable(CanonShaping::glyphDefinitionTable, CanonShaping::glyphDefinitionTableLen);
+      LEReferenceTo<GlyphDefinitionTableHeader> gdefTable(LETableReference::kStaticData,
+                                                          CanonShaping::glyphDefinitionTable,
+                                                          CanonShaping::glyphDefinitionTableLen);
         GDEFMarkFilter filter(gdefTable, success);
 
         adjustMarkGlyphs(&chars[offset], count, reverse, glyphStorage, &filter, success);
@@ -157,9 +159,9 @@
 UnicodeArabicOpenTypeLayoutEngine::UnicodeArabicOpenTypeLayoutEngine(const LEFontInstance *fontInstance, le_int32 scriptCode, le_int32 languageCode, le_int32 typoFlags, LEErrorCode &success)
   : ArabicOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags | LE_CHAR_FILTER_FEATURE_FLAG, success)
 {
-    fGSUBTable = (const GlyphSubstitutionTableHeader *) CanonShaping::glyphSubstitutionTable;
-    fGDEFTable = (const GlyphDefinitionTableHeader *) CanonShaping::glyphDefinitionTable;
-    /* OpenTypeLayoutEngine will allocate a substitution filter */
+  fGSUBTable.setTo(LETableReference::kStaticData, (const GlyphSubstitutionTableHeader *) CanonShaping::glyphSubstitutionTable, CanonShaping::glyphSubstitutionTableLen);
+  fGDEFTable.setTo(LETableReference::kStaticData, (const GlyphDefinitionTableHeader *) CanonShaping::glyphDefinitionTable, CanonShaping::glyphDefinitionTableLen);
+  /* OpenTypeLayoutEngine will allocate a substitution filter */
 }
 
 UnicodeArabicOpenTypeLayoutEngine::~UnicodeArabicOpenTypeLayoutEngine()
--- a/jdk/src/share/native/sun/font/layout/ArabicShaping.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ArabicShaping.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -59,7 +59,8 @@
 ArabicShaping::ShapeType ArabicShaping::getShapeType(LEUnicode c)
 {
   LEErrorCode success = LE_NO_ERROR;
-  const LEReferenceTo<ClassDefinitionTable> joiningTypes((const ClassDefinitionTable *) ArabicShaping::shapingTypeTable,
+  const LEReferenceTo<ClassDefinitionTable> joiningTypes(LETableReference::kStaticData,
+                                                         (const ClassDefinitionTable *) ArabicShaping::shapingTypeTable,
                                                          ArabicShaping::shapingTypeTableLen);
   le_int32 joiningType = joiningTypes->getGlyphClass(joiningTypes, c, success);
 
--- a/jdk/src/share/native/sun/font/layout/CanonShaping.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/CanonShaping.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -60,7 +60,7 @@
                                 LEUnicode *outChars, LEGlyphStorage &glyphStorage)
 {
     LEErrorCode success = LE_NO_ERROR;
-    LEReferenceTo<GlyphDefinitionTableHeader> gdefTable(CanonShaping::glyphDefinitionTable, CanonShaping::glyphDefinitionTableLen);
+    LEReferenceTo<GlyphDefinitionTableHeader> gdefTable(LETableReference::kStaticData, CanonShaping::glyphDefinitionTable, CanonShaping::glyphDefinitionTableLen);
     LEReferenceTo<ClassDefinitionTable> classTable = gdefTable->getMarkAttachClassDefinitionTable(gdefTable, success);
     le_int32 *combiningClasses = LE_NEW_ARRAY(le_int32, charCount);
     le_int32 *indices = LE_NEW_ARRAY(le_int32, charCount);
--- a/jdk/src/share/native/sun/font/layout/CharSubstitutionFilter.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/CharSubstitutionFilter.h	Fri Jan 10 15:04:46 2014 +0000
@@ -43,6 +43,8 @@
  * This filter is used by character-based GSUB processors. It
  * accepts only those characters which the given font can display.
  *
+ * Note: Implementation is in ArabicLayoutEngine.cpp
+ *
  * @internal
  */
 class CharSubstitutionFilter : public UMemory, public LEGlyphFilter
@@ -97,7 +99,7 @@
      *
      * @internal
      */
-    le_bool accept(LEGlyphID glyph) const;
+    le_bool accept(LEGlyphID glyph, LEErrorCode &success) const;
 };
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/ClassDefinitionTables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ClassDefinitionTables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -49,6 +49,7 @@
     le_int32  getGlyphClass(const LETableReference &base, LEGlyphID glyphID, LEErrorCode &success) const;
     le_bool   hasGlyphClass(const LETableReference &base, le_int32 glyphClass, LEErrorCode &success) const;
 
+#if LE_ENABLE_RAW
   le_int32 getGlyphClass(LEGlyphID glyphID) const {
     LETableReference base((const le_uint8*)this);
     LEErrorCode ignored = LE_NO_ERROR;
@@ -60,6 +61,7 @@
     LEErrorCode ignored = LE_NO_ERROR;
     return hasGlyphClass(base,glyphClass,ignored);
   }
+#endif
 };
 
 struct ClassDefFormat1Table : ClassDefinitionTable
--- a/jdk/src/share/native/sun/font/layout/ContextualSubstSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ContextualSubstSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -48,7 +48,7 @@
 */
 void ContextualSubstitutionBase::applySubstitutionLookups(
         const LookupProcessor *lookupProcessor,
-        const SubstitutionLookupRecord *substLookupRecordArray,
+        const LEReferenceToArrayOf<SubstitutionLookupRecord>& substLookupRecordArray,
         le_uint16 substCount,
         GlyphIterator *glyphIterator,
         const LEFontInstance *fontInstance,
@@ -60,10 +60,11 @@
     }
 
     GlyphIterator tempIterator(*glyphIterator);
+    const SubstitutionLookupRecord *substLookupRecordArrayPtr = substLookupRecordArray.getAlias(); // OK to dereference, range checked against substCount below.
 
     for (le_int16 subst = 0; subst < substCount && LE_SUCCESS(success); subst += 1) {
-        le_uint16 sequenceIndex = SWAPW(substLookupRecordArray[subst].sequenceIndex);
-        le_uint16 lookupListIndex = SWAPW(substLookupRecordArray[subst].lookupListIndex);
+        le_uint16 sequenceIndex = SWAPW(substLookupRecordArrayPtr[subst].sequenceIndex);
+        le_uint16 lookupListIndex = SWAPW(substLookupRecordArrayPtr[subst].lookupListIndex);
 
         tempIterator.setCurrStreamPosition(position);
         tempIterator.next(sequenceIndex);
@@ -72,7 +73,7 @@
     }
 }
 
-le_bool ContextualSubstitutionBase::matchGlyphIDs(const TTGlyphID *glyphArray, le_uint16 glyphCount,
+le_bool ContextualSubstitutionBase::matchGlyphIDs(const LEReferenceToArrayOf<TTGlyphID>& glyphArray, le_uint16 glyphCount,
                                                GlyphIterator *glyphIterator, le_bool backtrack)
 {
     le_int32 direction = 1;
@@ -101,10 +102,13 @@
     return TRUE;
 }
 
-le_bool ContextualSubstitutionBase::matchGlyphClasses(const le_uint16 *classArray, le_uint16 glyphCount,
-                                               GlyphIterator *glyphIterator,
-                                               const ClassDefinitionTable *classDefinitionTable,
-                                               le_bool backtrack)
+le_bool ContextualSubstitutionBase::matchGlyphClasses(
+    const LEReferenceToArrayOf<le_uint16> &classArray,
+    le_uint16 glyphCount,
+    GlyphIterator *glyphIterator,
+    const LEReferenceTo<ClassDefinitionTable> &classDefinitionTable,
+    LEErrorCode &success,
+    le_bool backtrack)
 {
     le_int32 direction = 1;
     le_int32 match = 0;
@@ -120,7 +124,7 @@
         }
 
         LEGlyphID glyph = glyphIterator->getCurrGlyphID();
-        le_int32 glyphClass = classDefinitionTable->getGlyphClass(glyph);
+        le_int32 glyphClass = classDefinitionTable->getGlyphClass(classDefinitionTable, glyph, success);
         le_int32 matchClass = SWAPW(classArray[match]);
 
         if (glyphClass != matchClass) {
@@ -128,7 +132,7 @@
             // in the class array which aren't in the class definition
             // table. If we're looking for such a class, pretend that
             // we found it.
-            if (classDefinitionTable->hasGlyphClass(matchClass)) {
+            if (classDefinitionTable->hasGlyphClass(classDefinitionTable, matchClass, success)) {
                 return FALSE;
             }
         }
@@ -140,8 +144,8 @@
     return TRUE;
 }
 
-le_bool ContextualSubstitutionBase::matchGlyphCoverages(const Offset *coverageTableOffsetArray, le_uint16 glyphCount,
-                                                     GlyphIterator *glyphIterator, const char *offsetBase, le_bool backtrack)
+le_bool ContextualSubstitutionBase::matchGlyphCoverages(const LEReferenceToArrayOf<Offset> &coverageTableOffsetArray, le_uint16 glyphCount,
+GlyphIterator *glyphIterator, const LETableReference &offsetBase, LEErrorCode &success, le_bool backtrack)
 {
     le_int32 direction = 1;
     le_int32 glyph = 0;
@@ -153,13 +157,15 @@
 
     while (glyphCount > 0) {
         Offset coverageTableOffset = SWAPW(coverageTableOffsetArray[glyph]);
-        const CoverageTable *coverageTable = (const CoverageTable *) (offsetBase + coverageTableOffset);
+        LEReferenceTo<CoverageTable> coverageTable(offsetBase, success, coverageTableOffset);
 
-        if (! glyphIterator->next()) {
+        if (LE_FAILURE(success) || ! glyphIterator->next()) {
             return FALSE;
         }
 
-        if (coverageTable->getGlyphCoverage((LEGlyphID) glyphIterator->getCurrGlyphID()) < 0) {
+        if (coverageTable->getGlyphCoverage(coverageTable,
+                                            (LEGlyphID) glyphIterator->getCurrGlyphID(),
+                                            success) < 0) {
             return FALSE;
         }
 
@@ -170,7 +176,7 @@
     return TRUE;
 }
 
-le_uint32 ContextualSubstitutionSubtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ContextualSubstitutionSubtable::process(const LETableReference &base, const LookupProcessor *lookupProcessor,
                                                   GlyphIterator *glyphIterator,
                                                   const LEFontInstance *fontInstance,
                                                   LEErrorCode& success) const
@@ -186,20 +192,29 @@
 
     case 1:
     {
-        const ContextualSubstitutionFormat1Subtable *subtable = (const ContextualSubstitutionFormat1Subtable *) this;
-        return subtable->process(lookupProcessor, glyphIterator, fontInstance, success);
+      LEReferenceTo<ContextualSubstitutionFormat1Subtable> subtable(base, success, (const ContextualSubstitutionFormat1Subtable *) this);
+      if( LE_FAILURE(success) ) {
+        return 0;
+      }
+      return subtable->process(subtable, lookupProcessor, glyphIterator, fontInstance, success);
     }
 
     case 2:
     {
-        const ContextualSubstitutionFormat2Subtable *subtable = (const ContextualSubstitutionFormat2Subtable *) this;
-        return subtable->process(lookupProcessor, glyphIterator, fontInstance, success);
+      LEReferenceTo<ContextualSubstitutionFormat2Subtable> subtable(base, success, (const ContextualSubstitutionFormat2Subtable *) this);
+      if( LE_FAILURE(success) ) {
+        return 0;
+      }
+      return subtable->process(subtable, lookupProcessor, glyphIterator, fontInstance, success);
     }
 
     case 3:
     {
-        const ContextualSubstitutionFormat3Subtable *subtable = (const ContextualSubstitutionFormat3Subtable *) this;
-        return subtable->process(lookupProcessor, glyphIterator, fontInstance, success);
+      LEReferenceTo<ContextualSubstitutionFormat3Subtable> subtable(base, success, (const ContextualSubstitutionFormat3Subtable *) this);
+      if( LE_FAILURE(success) ) {
+        return 0;
+      }
+      return subtable->process(subtable, lookupProcessor, glyphIterator, fontInstance, success);
     }
 
     default:
@@ -207,7 +222,7 @@
     }
 }
 
-le_uint32 ContextualSubstitutionFormat1Subtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ContextualSubstitutionFormat1Subtable::process(const LETableReference &base, const LookupProcessor *lookupProcessor,
                                                          GlyphIterator *glyphIterator,
                                                          const LEFontInstance *fontInstance,
                                                          LEErrorCode& success) const
@@ -227,22 +242,22 @@
 
         if (coverageIndex < srSetCount) {
             Offset subRuleSetTableOffset = SWAPW(subRuleSetTableOffsetArray[coverageIndex]);
-            const SubRuleSetTable *subRuleSetTable =
-                (const SubRuleSetTable *) ((char *) this + subRuleSetTableOffset);
+            LEReferenceTo<SubRuleSetTable>
+                 subRuleSetTable(base, success, (const SubRuleSetTable *) ((char *) this + subRuleSetTableOffset));
             le_uint16 subRuleCount = SWAPW(subRuleSetTable->subRuleCount);
             le_int32 position = glyphIterator->getCurrStreamPosition();
 
             for (le_uint16 subRule = 0; subRule < subRuleCount; subRule += 1) {
                 Offset subRuleTableOffset =
                     SWAPW(subRuleSetTable->subRuleTableOffsetArray[subRule]);
-                const SubRuleTable *subRuleTable =
-                    (const SubRuleTable *) ((char *) subRuleSetTable + subRuleTableOffset);
+                LEReferenceTo<SubRuleTable>
+                     subRuleTable(subRuleSetTable, success, subRuleTableOffset);
                 le_uint16 matchCount = SWAPW(subRuleTable->glyphCount) - 1;
                 le_uint16 substCount = SWAPW(subRuleTable->substCount);
-
-                if (matchGlyphIDs(subRuleTable->inputGlyphArray, matchCount, glyphIterator)) {
-                    const SubstitutionLookupRecord *substLookupRecordArray =
-                        (const SubstitutionLookupRecord *) &subRuleTable->inputGlyphArray[matchCount];
+                LEReferenceToArrayOf<TTGlyphID> inputGlyphArray(base, success, subRuleTable->inputGlyphArray, matchCount+2);
+                if (matchGlyphIDs(inputGlyphArray, matchCount, glyphIterator)) {
+                  LEReferenceToArrayOf<SubstitutionLookupRecord>
+                    substLookupRecordArray(base, success, (const SubstitutionLookupRecord *) &subRuleTable->inputGlyphArray[matchCount], substCount);
 
                     applySubstitutionLookups(lookupProcessor, substLookupRecordArray, substCount, glyphIterator, fontInstance, position, success);
 
@@ -259,10 +274,11 @@
     return 0;
 }
 
-le_uint32 ContextualSubstitutionFormat2Subtable::process(const LookupProcessor *lookupProcessor,
-                                                         GlyphIterator *glyphIterator,
-                                                         const LEFontInstance *fontInstance,
-                                                         LEErrorCode& success) const
+le_uint32 ContextualSubstitutionFormat2Subtable::process(const LETableReference &base,
+         const LookupProcessor *lookupProcessor,
+         GlyphIterator *glyphIterator,
+         const LEFontInstance *fontInstance,
+         LEErrorCode& success) const
 {
     if (LE_FAILURE(success)) {
         return 0;
@@ -275,29 +291,33 @@
     }
 
     if (coverageIndex >= 0) {
-        const ClassDefinitionTable *classDefinitionTable =
-            (const ClassDefinitionTable *) ((char *) this + SWAPW(classDefTableOffset));
+        LEReferenceTo<ClassDefinitionTable> classDefinitionTable(base, success,
+                                                                 (const ClassDefinitionTable *) ((char *) this + SWAPW(classDefTableOffset)));
         le_uint16 scSetCount = SWAPW(subClassSetCount);
-        le_int32 setClass = classDefinitionTable->getGlyphClass(glyphIterator->getCurrGlyphID());
+        le_int32 setClass = classDefinitionTable->getGlyphClass(classDefinitionTable,
+                                                                glyphIterator->getCurrGlyphID(),
+                                                                success);
 
         if (setClass < scSetCount && subClassSetTableOffsetArray[setClass] != 0) {
             Offset subClassSetTableOffset = SWAPW(subClassSetTableOffsetArray[setClass]);
-            const SubClassSetTable *subClassSetTable =
-                (const SubClassSetTable *) ((char *) this + subClassSetTableOffset);
+            LEReferenceTo<SubClassSetTable>
+                 subClassSetTable(base, success, (const SubClassSetTable *) ((char *) this + subClassSetTableOffset));
             le_uint16 subClassRuleCount = SWAPW(subClassSetTable->subClassRuleCount);
             le_int32 position = glyphIterator->getCurrStreamPosition();
 
             for (le_uint16 scRule = 0; scRule < subClassRuleCount; scRule += 1) {
                 Offset subClassRuleTableOffset =
                     SWAPW(subClassSetTable->subClassRuleTableOffsetArray[scRule]);
-                const SubClassRuleTable *subClassRuleTable =
-                    (const SubClassRuleTable *) ((char *) subClassSetTable + subClassRuleTableOffset);
+                LEReferenceTo<SubClassRuleTable>
+                     subClassRuleTable(subClassSetTable, success, subClassRuleTableOffset);
                 le_uint16 matchCount = SWAPW(subClassRuleTable->glyphCount) - 1;
                 le_uint16 substCount = SWAPW(subClassRuleTable->substCount);
 
-                if (matchGlyphClasses(subClassRuleTable->classArray, matchCount, glyphIterator, classDefinitionTable)) {
-                    const SubstitutionLookupRecord *substLookupRecordArray =
-                        (const SubstitutionLookupRecord *) &subClassRuleTable->classArray[matchCount];
+                LEReferenceToArrayOf<le_uint16> classArray(base, success, subClassRuleTable->classArray, matchCount+1);
+
+                if (matchGlyphClasses(classArray, matchCount, glyphIterator, classDefinitionTable, success)) {
+                    LEReferenceToArrayOf<SubstitutionLookupRecord>
+                      substLookupRecordArray(base, success, (const SubstitutionLookupRecord *) &subClassRuleTable->classArray[matchCount], substCount);
 
                     applySubstitutionLookups(lookupProcessor, substLookupRecordArray, substCount, glyphIterator, fontInstance, position, success);
 
@@ -314,7 +334,8 @@
     return 0;
 }
 
-le_uint32 ContextualSubstitutionFormat3Subtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ContextualSubstitutionFormat3Subtable::process(const LETableReference &base,
+                                                         const LookupProcessor *lookupProcessor,
                                                          GlyphIterator *glyphIterator,
                                                          const LEFontInstance *fontInstance,
                                                          LEErrorCode& success)const
@@ -333,9 +354,13 @@
     // that matched when we're done.
     glyphIterator->prev();
 
-    if (ContextualSubstitutionBase::matchGlyphCoverages(coverageTableOffsetArray, gCount, glyphIterator, (const char *) this)) {
-        const SubstitutionLookupRecord *substLookupRecordArray =
-            (const SubstitutionLookupRecord *) &coverageTableOffsetArray[gCount];
+    LEReferenceToArrayOf<Offset> covTableOffsetArray(base, success, coverageTableOffsetArray, gCount);
+
+    if( LE_FAILURE(success) ) { return 0; }
+
+    if (ContextualSubstitutionBase::matchGlyphCoverages(covTableOffsetArray, gCount, glyphIterator, base, success)) {
+        LEReferenceToArrayOf<SubstitutionLookupRecord>
+          substLookupRecordArray(base, success, (const SubstitutionLookupRecord *) &coverageTableOffsetArray[gCount], subCount);
 
         ContextualSubstitutionBase::applySubstitutionLookups(lookupProcessor, substLookupRecordArray, subCount, glyphIterator, fontInstance, position, success);
 
@@ -347,7 +372,8 @@
     return 0;
 }
 
-le_uint32 ChainingContextualSubstitutionSubtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ChainingContextualSubstitutionSubtable::process(const LEReferenceTo<ChainingContextualSubstitutionSubtable> &base,
+                                                          const LookupProcessor *lookupProcessor,
                                                           GlyphIterator *glyphIterator,
                                                           const LEFontInstance *fontInstance,
                                                           LEErrorCode& success) const
@@ -363,20 +389,23 @@
 
     case 1:
     {
-        const ChainingContextualSubstitutionFormat1Subtable *subtable = (const ChainingContextualSubstitutionFormat1Subtable *) this;
-        return subtable->process(lookupProcessor, glyphIterator, fontInstance, success);
+      LEReferenceTo<ChainingContextualSubstitutionFormat1Subtable> subtable(base, success,  (ChainingContextualSubstitutionFormat1Subtable *) this);
+      if(LE_FAILURE(success)) return 0;
+      return subtable->process(subtable, lookupProcessor, glyphIterator, fontInstance, success);
     }
 
     case 2:
     {
-        const ChainingContextualSubstitutionFormat2Subtable *subtable = (const ChainingContextualSubstitutionFormat2Subtable *) this;
-        return subtable->process(lookupProcessor, glyphIterator, fontInstance, success);
+      LEReferenceTo<ChainingContextualSubstitutionFormat2Subtable> subtable(base, success, (const ChainingContextualSubstitutionFormat2Subtable *) this);
+      if( LE_FAILURE(success) ) { return 0; }
+      return subtable->process(subtable, lookupProcessor, glyphIterator, fontInstance, success);
     }
 
     case 3:
     {
-        const ChainingContextualSubstitutionFormat3Subtable *subtable = (const ChainingContextualSubstitutionFormat3Subtable *) this;
-        return subtable->process(lookupProcessor, glyphIterator, fontInstance, success);
+      LEReferenceTo<ChainingContextualSubstitutionFormat3Subtable> subtable(base, success, (const ChainingContextualSubstitutionFormat3Subtable *) this);
+      if( LE_FAILURE(success) ) { return 0; }
+      return subtable->process(subtable, lookupProcessor, glyphIterator, fontInstance, success);
     }
 
     default:
@@ -390,7 +419,7 @@
 // emptyFeatureList matches an le_uint32 or an le_uint16...
 static const FeatureMask emptyFeatureList = 0x00000000UL;
 
-le_uint32 ChainingContextualSubstitutionFormat1Subtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ChainingContextualSubstitutionFormat1Subtable::process(const LETableReference &base, const LookupProcessor *lookupProcessor,
                                                                  GlyphIterator *glyphIterator,
                                                                  const LEFontInstance *fontInstance,
                                                                  LEErrorCode& success) const
@@ -410,8 +439,8 @@
 
         if (coverageIndex < srSetCount) {
             Offset chainSubRuleSetTableOffset = SWAPW(chainSubRuleSetTableOffsetArray[coverageIndex]);
-            const ChainSubRuleSetTable *chainSubRuleSetTable =
-                (const ChainSubRuleSetTable *) ((char *) this + chainSubRuleSetTableOffset);
+            LEReferenceTo<ChainSubRuleSetTable>
+                 chainSubRuleSetTable(base, success, (const ChainSubRuleSetTable *) ((char *) this + chainSubRuleSetTableOffset));
             le_uint16 chainSubRuleCount = SWAPW(chainSubRuleSetTable->chainSubRuleCount);
             le_int32 position = glyphIterator->getCurrStreamPosition();
             GlyphIterator tempIterator(*glyphIterator, emptyFeatureList);
@@ -419,13 +448,19 @@
             for (le_uint16 subRule = 0; subRule < chainSubRuleCount; subRule += 1) {
                 Offset chainSubRuleTableOffset =
                     SWAPW(chainSubRuleSetTable->chainSubRuleTableOffsetArray[subRule]);
-                const ChainSubRuleTable *chainSubRuleTable =
-                    (const ChainSubRuleTable *) ((char *) chainSubRuleSetTable + chainSubRuleTableOffset);
+                LEReferenceTo<ChainSubRuleTable>
+                     chainSubRuleTable = LEReferenceTo<ChainSubRuleTable>(chainSubRuleSetTable, success, chainSubRuleTableOffset);
+                if( LE_FAILURE(success) ) { return 0; }
                 le_uint16 backtrackGlyphCount = SWAPW(chainSubRuleTable->backtrackGlyphCount);
+                LEReferenceToArrayOf<TTGlyphID> backtrackGlyphArray(base, success, chainSubRuleTable->backtrackGlyphArray, backtrackGlyphCount);
+                if( LE_FAILURE(success) ) { return 0; }
                 le_uint16 inputGlyphCount = (le_uint16) SWAPW(chainSubRuleTable->backtrackGlyphArray[backtrackGlyphCount]) - 1;
-                const TTGlyphID *inputGlyphArray = &chainSubRuleTable->backtrackGlyphArray[backtrackGlyphCount + 1];
+                LEReferenceToArrayOf<TTGlyphID>   inputGlyphArray(base, success, &chainSubRuleTable->backtrackGlyphArray[backtrackGlyphCount + 1], inputGlyphCount+2);
+
+                if( LE_FAILURE(success) ) { return 0; }
                 le_uint16 lookaheadGlyphCount = (le_uint16) SWAPW(inputGlyphArray[inputGlyphCount]);
-                const TTGlyphID *lookaheadGlyphArray = &inputGlyphArray[inputGlyphCount + 1];
+                LEReferenceToArrayOf<TTGlyphID>   lookaheadGlyphArray(base, success, inputGlyphArray.getAlias(inputGlyphCount + 1,success), lookaheadGlyphCount+2);
+                if( LE_FAILURE(success) ) { return 0; }
                 le_uint16 substCount = (le_uint16) SWAPW(lookaheadGlyphArray[lookaheadGlyphCount]);
 
                 tempIterator.setCurrStreamPosition(position);
@@ -435,7 +470,8 @@
                 }
 
                 tempIterator.prev();
-                if (! matchGlyphIDs(chainSubRuleTable->backtrackGlyphArray, backtrackGlyphCount, &tempIterator, TRUE)) {
+
+                if (! matchGlyphIDs(backtrackGlyphArray, backtrackGlyphCount, &tempIterator, TRUE)) {
                     continue;
                 }
 
@@ -446,8 +482,8 @@
                 }
 
                 if (matchGlyphIDs(inputGlyphArray, inputGlyphCount, glyphIterator)) {
-                    const SubstitutionLookupRecord *substLookupRecordArray =
-                        (const SubstitutionLookupRecord *) &lookaheadGlyphArray[lookaheadGlyphCount + 1];
+                    LEReferenceToArrayOf<SubstitutionLookupRecord>
+                      substLookupRecordArray(base, success, (const SubstitutionLookupRecord *) lookaheadGlyphArray.getAlias(lookaheadGlyphCount + 1,success), substCount);
 
                     applySubstitutionLookups(lookupProcessor, substLookupRecordArray, substCount, glyphIterator, fontInstance, position, success);
 
@@ -464,7 +500,7 @@
     return 0;
 }
 
-le_uint32 ChainingContextualSubstitutionFormat2Subtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ChainingContextualSubstitutionFormat2Subtable::process(const LETableReference &base, const LookupProcessor *lookupProcessor,
                                                                  GlyphIterator *glyphIterator,
                                                                  const LEFontInstance *fontInstance,
                                                                  LEErrorCode& success) const
@@ -480,19 +516,21 @@
     }
 
     if (coverageIndex >= 0) {
-        const ClassDefinitionTable *backtrackClassDefinitionTable =
-            (const ClassDefinitionTable *) ((char *) this + SWAPW(backtrackClassDefTableOffset));
-        const ClassDefinitionTable *inputClassDefinitionTable =
-            (const ClassDefinitionTable *) ((char *) this + SWAPW(inputClassDefTableOffset));
-        const ClassDefinitionTable *lookaheadClassDefinitionTable =
-            (const ClassDefinitionTable *) ((char *) this + SWAPW(lookaheadClassDefTableOffset));
+        LEReferenceTo<ClassDefinitionTable>
+             backtrackClassDefinitionTable(base, success, (const ClassDefinitionTable *) ((char *) this + SWAPW(backtrackClassDefTableOffset)));
+        LEReferenceTo<ClassDefinitionTable>
+             inputClassDefinitionTable(base, success, (const ClassDefinitionTable *) ((char *) this + SWAPW(inputClassDefTableOffset)));
+        LEReferenceTo<ClassDefinitionTable>
+             lookaheadClassDefinitionTable(base, success, (const ClassDefinitionTable *) ((char *) this + SWAPW(lookaheadClassDefTableOffset)));
         le_uint16 scSetCount = SWAPW(chainSubClassSetCount);
-        le_int32 setClass = inputClassDefinitionTable->getGlyphClass(glyphIterator->getCurrGlyphID());
+        le_int32 setClass = inputClassDefinitionTable->getGlyphClass(inputClassDefinitionTable,
+                                                                     glyphIterator->getCurrGlyphID(),
+                                                                     success);
 
         if (setClass < scSetCount && chainSubClassSetTableOffsetArray[setClass] != 0) {
             Offset chainSubClassSetTableOffset = SWAPW(chainSubClassSetTableOffsetArray[setClass]);
-            const ChainSubClassSetTable *chainSubClassSetTable =
-                (const ChainSubClassSetTable *) ((char *) this + chainSubClassSetTableOffset);
+            LEReferenceTo<ChainSubClassSetTable>
+                 chainSubClassSetTable(base, success, (const ChainSubClassSetTable *) ((char *) this + chainSubClassSetTableOffset));
             le_uint16 chainSubClassRuleCount = SWAPW(chainSubClassSetTable->chainSubClassRuleCount);
             le_int32 position = glyphIterator->getCurrStreamPosition();
             GlyphIterator tempIterator(*glyphIterator, emptyFeatureList);
@@ -500,13 +538,15 @@
             for (le_uint16 scRule = 0; scRule < chainSubClassRuleCount; scRule += 1) {
                 Offset chainSubClassRuleTableOffset =
                     SWAPW(chainSubClassSetTable->chainSubClassRuleTableOffsetArray[scRule]);
-                const ChainSubClassRuleTable *chainSubClassRuleTable =
-                    (const ChainSubClassRuleTable *) ((char *) chainSubClassSetTable + chainSubClassRuleTableOffset);
+                LEReferenceTo<ChainSubClassRuleTable>
+                     chainSubClassRuleTable(chainSubClassSetTable, success, chainSubClassRuleTableOffset);
                 le_uint16 backtrackGlyphCount = SWAPW(chainSubClassRuleTable->backtrackGlyphCount);
                 le_uint16 inputGlyphCount = SWAPW(chainSubClassRuleTable->backtrackClassArray[backtrackGlyphCount]) - 1;
-                const le_uint16 *inputClassArray = &chainSubClassRuleTable->backtrackClassArray[backtrackGlyphCount + 1];
-                le_uint16 lookaheadGlyphCount = SWAPW(inputClassArray[inputGlyphCount]);
-                const le_uint16 *lookaheadClassArray = &inputClassArray[inputGlyphCount + 1];
+                LEReferenceToArrayOf<le_uint16>   inputClassArray(base, success, &chainSubClassRuleTable->backtrackClassArray[backtrackGlyphCount + 1],inputGlyphCount+2); // +2 for the lookaheadGlyphCount count
+                le_uint16 lookaheadGlyphCount = SWAPW(inputClassArray.getObject(inputGlyphCount, success));
+                LEReferenceToArrayOf<le_uint16>   lookaheadClassArray(base, success, inputClassArray.getAlias(inputGlyphCount + 1,success), lookaheadGlyphCount+2); // +2 for the substCount
+
+                if( LE_FAILURE(success) ) { return 0; }
                 le_uint16 substCount = SWAPW(lookaheadClassArray[lookaheadGlyphCount]);
 
 
@@ -517,20 +557,22 @@
                 }
 
                 tempIterator.prev();
-                if (! matchGlyphClasses(chainSubClassRuleTable->backtrackClassArray, backtrackGlyphCount,
-                    &tempIterator, backtrackClassDefinitionTable, TRUE)) {
+                LEReferenceToArrayOf<le_uint16>   backtrackClassArray(base, success, chainSubClassRuleTable->backtrackClassArray, backtrackGlyphCount);
+                if( LE_FAILURE(success) ) { return 0; }
+                if (! matchGlyphClasses(backtrackClassArray, backtrackGlyphCount,
+                                        &tempIterator, backtrackClassDefinitionTable, success, TRUE)) {
                     continue;
                 }
 
                 tempIterator.setCurrStreamPosition(position);
                 tempIterator.next(inputGlyphCount);
-                if (! matchGlyphClasses(lookaheadClassArray, lookaheadGlyphCount, &tempIterator, lookaheadClassDefinitionTable)) {
+                if (! matchGlyphClasses(lookaheadClassArray, lookaheadGlyphCount, &tempIterator, lookaheadClassDefinitionTable, success)) {
                     continue;
                 }
 
-                if (matchGlyphClasses(inputClassArray, inputGlyphCount, glyphIterator, inputClassDefinitionTable)) {
-                    const SubstitutionLookupRecord *substLookupRecordArray =
-                        (const SubstitutionLookupRecord *) &lookaheadClassArray[lookaheadGlyphCount + 1];
+                if (matchGlyphClasses(inputClassArray, inputGlyphCount, glyphIterator, inputClassDefinitionTable, success)) {
+                    LEReferenceToArrayOf<SubstitutionLookupRecord>
+                      substLookupRecordArray(base, success, (const SubstitutionLookupRecord *) lookaheadClassArray.getAlias(lookaheadGlyphCount + 1, success), substCount);
 
                     applySubstitutionLookups(lookupProcessor, substLookupRecordArray, substCount, glyphIterator, fontInstance, position, success);
 
@@ -547,7 +589,7 @@
     return 0;
 }
 
-le_uint32 ChainingContextualSubstitutionFormat3Subtable::process(const LookupProcessor *lookupProcessor,
+le_uint32 ChainingContextualSubstitutionFormat3Subtable::process(const LETableReference &base, const LookupProcessor *lookupProcessor,
                                                                  GlyphIterator *glyphIterator,
                                                                  const LEFontInstance *fontInstance,
                                                                  LEErrorCode & success) const
@@ -558,9 +600,13 @@
 
     le_uint16 backtrkGlyphCount = SWAPW(backtrackGlyphCount);
     le_uint16 inputGlyphCount = (le_uint16) SWAPW(backtrackCoverageTableOffsetArray[backtrkGlyphCount]);
-    const Offset *inputCoverageTableOffsetArray = &backtrackCoverageTableOffsetArray[backtrkGlyphCount + 1];
+    LEReferenceToArrayOf<Offset>   inputCoverageTableOffsetArray(base, success, &backtrackCoverageTableOffsetArray[backtrkGlyphCount + 1], inputGlyphCount+2); // offset
     const le_uint16 lookaheadGlyphCount = (le_uint16) SWAPW(inputCoverageTableOffsetArray[inputGlyphCount]);
-    const Offset *lookaheadCoverageTableOffsetArray = &inputCoverageTableOffsetArray[inputGlyphCount + 1];
+
+    if( LE_FAILURE(success) ) { return 0; }
+    LEReferenceToArrayOf<Offset>   lookaheadCoverageTableOffsetArray(base, success, inputCoverageTableOffsetArray.getAlias(inputGlyphCount + 1, success), lookaheadGlyphCount+2);
+
+    if( LE_FAILURE(success) ) { return 0; }
     le_uint16 substCount = (le_uint16) SWAPW(lookaheadCoverageTableOffsetArray[lookaheadGlyphCount]);
     le_int32 position = glyphIterator->getCurrStreamPosition();
     GlyphIterator tempIterator(*glyphIterator, emptyFeatureList);
@@ -571,14 +617,14 @@
 
     tempIterator.prev();
     if (! ContextualSubstitutionBase::matchGlyphCoverages(backtrackCoverageTableOffsetArray,
-        backtrkGlyphCount, &tempIterator, (const char *) this, TRUE)) {
+                       backtrkGlyphCount, &tempIterator, base, success, TRUE)) {
         return 0;
     }
 
     tempIterator.setCurrStreamPosition(position);
     tempIterator.next(inputGlyphCount - 1);
     if (! ContextualSubstitutionBase::matchGlyphCoverages(lookaheadCoverageTableOffsetArray,
-        lookaheadGlyphCount, &tempIterator, (const char *) this)) {
+                        lookaheadGlyphCount, &tempIterator, base, success)) {
         return 0;
     }
 
@@ -589,9 +635,10 @@
     glyphIterator->prev();
 
     if (ContextualSubstitutionBase::matchGlyphCoverages(inputCoverageTableOffsetArray,
-        inputGlyphCount, glyphIterator, (const char *) this)) {
-        const SubstitutionLookupRecord *substLookupRecordArray =
-            (const SubstitutionLookupRecord *) &lookaheadCoverageTableOffsetArray[lookaheadGlyphCount + 1];
+                                                        inputGlyphCount, glyphIterator, base, success)) {
+        LEReferenceToArrayOf<SubstitutionLookupRecord>
+          substLookupRecordArray(base, success,
+                                 (const SubstitutionLookupRecord *) lookaheadCoverageTableOffsetArray.getAlias(lookaheadGlyphCount + 1,success), substCount);
 
         ContextualSubstitutionBase::applySubstitutionLookups(lookupProcessor, substLookupRecordArray, substCount, glyphIterator, fontInstance, position, success);
 
--- a/jdk/src/share/native/sun/font/layout/ContextualSubstSubtables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ContextualSubstSubtables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -56,20 +56,32 @@
 struct ContextualSubstitutionBase : GlyphSubstitutionSubtable
 {
     static le_bool matchGlyphIDs(
-        const TTGlyphID *glyphArray, le_uint16 glyphCount, GlyphIterator *glyphIterator,
+                                 const LEReferenceToArrayOf<TTGlyphID> &glyphArray, le_uint16 glyphCount, GlyphIterator *glyphIterator,
         le_bool backtrack = FALSE);
 
     static le_bool matchGlyphClasses(
-        const le_uint16 *classArray, le_uint16 glyphCount, GlyphIterator *glyphIterator,
-        const ClassDefinitionTable *classDefinitionTable, le_bool backtrack = FALSE);
+                                     const LEReferenceToArrayOf<le_uint16> &classArray, le_uint16 glyphCount, GlyphIterator *glyphIterator,
+        const LEReferenceTo<ClassDefinitionTable> &classDefinitionTable, LEErrorCode &success, le_bool backtrack = FALSE);
 
     static le_bool matchGlyphCoverages(
-        const Offset *coverageTableOffsetArray, le_uint16 glyphCount,
-        GlyphIterator *glyphIterator, const char *offsetBase, le_bool backtrack = FALSE);
+                                       const LEReferenceToArrayOf<Offset> &coverageTableOffsetArray, le_uint16 glyphCount,
+        GlyphIterator *glyphIterator, const LETableReference& offsetBase, LEErrorCode &success, le_bool backtrack = FALSE);
+
+    /**
+     * little shim to wrap the Offset array in range checking
+     * @private
+     */
+    static le_bool matchGlyphCoverages(
+                                       const Offset *coverageTableOffsetArray, le_uint16 glyphCount,
+                                       GlyphIterator *glyphIterator, const LETableReference& offsetBase, LEErrorCode &success, le_bool backtrack = FALSE) {
+      LEReferenceToArrayOf<Offset> ref(offsetBase, success, coverageTableOffsetArray, glyphCount);
+      if( LE_FAILURE(success) ) { return FALSE; }
+      return matchGlyphCoverages(ref, glyphCount, glyphIterator, offsetBase, success, backtrack);
+    }
 
     static void applySubstitutionLookups(
         const LookupProcessor *lookupProcessor,
-        const SubstitutionLookupRecord *substLookupRecordArray,
+        const LEReferenceToArrayOf<SubstitutionLookupRecord>& substLookupRecordArray,
         le_uint16 substCount,
         GlyphIterator *glyphIterator,
         const LEFontInstance *fontInstance,
@@ -79,7 +91,8 @@
 
 struct ContextualSubstitutionSubtable : ContextualSubstitutionBase
 {
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor,
+                       GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 
 struct ContextualSubstitutionFormat1Subtable : ContextualSubstitutionSubtable
@@ -87,7 +100,8 @@
     le_uint16  subRuleSetCount;
     Offset  subRuleSetTableOffsetArray[ANY_NUMBER];
 
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator,
+                       const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 LE_VAR_ARRAY(ContextualSubstitutionFormat1Subtable, subRuleSetTableOffsetArray)
 
@@ -116,7 +130,7 @@
     le_uint16  subClassSetCount;
     Offset  subClassSetTableOffsetArray[ANY_NUMBER];
 
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 LE_VAR_ARRAY(ContextualSubstitutionFormat2Subtable, subClassSetTableOffsetArray)
 
@@ -152,13 +166,15 @@
     Offset  coverageTableOffsetArray[ANY_NUMBER];
   //SubstitutionLookupRecord substLookupRecord[ANY_NUMBER];
 
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator,
+                       const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 LE_VAR_ARRAY(ContextualSubstitutionFormat3Subtable, coverageTableOffsetArray)
 
 struct ChainingContextualSubstitutionSubtable : ContextualSubstitutionBase
 {
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LEReferenceTo<ChainingContextualSubstitutionSubtable> &base, const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator,
+                       const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 
 struct ChainingContextualSubstitutionFormat1Subtable : ChainingContextualSubstitutionSubtable
@@ -166,7 +182,8 @@
     le_uint16  chainSubRuleSetCount;
     Offset  chainSubRuleSetTableOffsetArray[ANY_NUMBER];
 
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator,
+                       const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 LE_VAR_ARRAY(ChainingContextualSubstitutionFormat1Subtable, chainSubRuleSetTableOffsetArray)
 
@@ -201,7 +218,8 @@
     le_uint16  chainSubClassSetCount;
     Offset  chainSubClassSetTableOffsetArray[ANY_NUMBER];
 
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator,
+                       const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 LE_VAR_ARRAY(ChainingContextualSubstitutionFormat2Subtable, chainSubClassSetTableOffsetArray)
 
@@ -243,7 +261,8 @@
   //le_uint16  substCount;
   //SubstitutionLookupRecord substLookupRecord[ANY_NUMBER];
 
-    le_uint32  process(const LookupProcessor *lookupProcessor, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
+    le_uint32  process(const LETableReference &base, const LookupProcessor *lookupProcessor,
+                       GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 LE_VAR_ARRAY(ChainingContextualSubstitutionFormat3Subtable, backtrackCoverageTableOffsetArray)
 
--- a/jdk/src/share/native/sun/font/layout/CoverageTables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/CoverageTables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -37,8 +37,10 @@
 
 U_NAMESPACE_BEGIN
 
-le_int32 CoverageTable::getGlyphCoverage(LEGlyphID glyphID) const
+le_int32 CoverageTable::getGlyphCoverage(const LETableReference &base, LEGlyphID glyphID, LEErrorCode &success) const
 {
+  if(LE_FAILURE(success)) return -1;
+
     switch(SWAPW(coverageFormat))
     {
     case 0:
@@ -46,16 +48,16 @@
 
     case 1:
     {
-        const CoverageFormat1Table *f1Table = (const CoverageFormat1Table *) this;
+      LEReferenceTo<CoverageFormat1Table> f1Table(base, success);
 
-        return f1Table->getGlyphCoverage(glyphID);
+      return f1Table->getGlyphCoverage(f1Table, glyphID, success);
     }
 
     case 2:
     {
-        const CoverageFormat2Table *f2Table = (const CoverageFormat2Table *) this;
+      LEReferenceTo<CoverageFormat2Table> f2Table(base, success);
 
-        return f2Table->getGlyphCoverage(glyphID);
+      return f2Table->getGlyphCoverage(f2Table, glyphID, success);
     }
 
     default:
@@ -63,8 +65,10 @@
     }
 }
 
-le_int32 CoverageFormat1Table::getGlyphCoverage(LEGlyphID glyphID) const
+le_int32 CoverageFormat1Table::getGlyphCoverage(LEReferenceTo<CoverageFormat1Table> &base, LEGlyphID glyphID, LEErrorCode &success) const
 {
+  if(LE_FAILURE(success)) return -1;
+
     TTGlyphID ttGlyphID = (TTGlyphID) LE_GET_GLYPH(glyphID);
     le_uint16 count = SWAPW(glyphCount);
     le_uint8 bit = OpenTypeUtilities::highBit(count);
@@ -73,37 +77,45 @@
     le_uint16 probe = power;
     le_uint16 index = 0;
 
-        if (count == 0) {
-                return -1;
-        }
+    if (count == 0) {
+      return -1;
+    }
+
+    LEReferenceToArrayOf<TTGlyphID>(base, success, glyphArray, count);
+    if(LE_FAILURE(success)) return -1;  // range checks array
+
 
     if (SWAPW(glyphArray[extra]) <= ttGlyphID) {
-        index = extra;
+      index = extra;
     }
 
     while (probe > (1 << 0)) {
-        probe >>= 1;
+      probe >>= 1;
 
-        if (SWAPW(glyphArray[index + probe]) <= ttGlyphID) {
-            index += probe;
-        }
+      if (SWAPW(glyphArray[index + probe]) <= ttGlyphID) {
+        index += probe;
+      }
     }
 
     if (SWAPW(glyphArray[index]) == ttGlyphID) {
-        return index;
+      return index;
     }
 
     return -1;
 }
 
-le_int32 CoverageFormat2Table::getGlyphCoverage(LEGlyphID glyphID) const
+le_int32 CoverageFormat2Table::getGlyphCoverage(LEReferenceTo<CoverageFormat2Table> &base, LEGlyphID glyphID, LEErrorCode &success) const
 {
+  if(LE_FAILURE(success)) return -1;
+
     TTGlyphID ttGlyphID = (TTGlyphID) LE_GET_GLYPH(glyphID);
     le_uint16 count = SWAPW(rangeCount);
+
+    LEReferenceToArrayOf<GlyphRangeRecord> rangeRecordArrayRef(base, success, rangeRecordArray, count);
     le_int32 rangeIndex =
-        OpenTypeUtilities::getGlyphRangeIndex(ttGlyphID, rangeRecordArray, count);
+        OpenTypeUtilities::getGlyphRangeIndex(ttGlyphID, rangeRecordArrayRef, success);
 
-    if (rangeIndex < 0) {
+    if (rangeIndex < 0 || LE_FAILURE(success)) { // could fail if array out of bounds
         return -1;
     }
 
--- a/jdk/src/share/native/sun/font/layout/CoverageTables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/CoverageTables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -46,7 +46,7 @@
 {
     le_uint16 coverageFormat;
 
-    le_int32 getGlyphCoverage(LEGlyphID glyphID) const;
+    le_int32 getGlyphCoverage(const LETableReference &base, LEGlyphID glyphID, LEErrorCode &success) const;
 };
 
 struct CoverageFormat1Table : CoverageTable
@@ -54,7 +54,7 @@
     le_uint16  glyphCount;
     TTGlyphID glyphArray[ANY_NUMBER];
 
-    le_int32 getGlyphCoverage(LEGlyphID glyphID) const;
+    le_int32 getGlyphCoverage(LEReferenceTo<CoverageFormat1Table> &base, LEGlyphID glyphID, LEErrorCode &success) const;
 };
 LE_VAR_ARRAY(CoverageFormat1Table, glyphArray)
 
@@ -64,7 +64,7 @@
     le_uint16        rangeCount;
     GlyphRangeRecord rangeRecordArray[ANY_NUMBER];
 
-    le_int32 getGlyphCoverage(LEGlyphID glyphID) const;
+    le_int32 getGlyphCoverage(LEReferenceTo<CoverageFormat2Table> &base, LEGlyphID glyphID, LEErrorCode &success) const;
 };
 LE_VAR_ARRAY(CoverageFormat2Table, rangeRecordArray)
 
--- a/jdk/src/share/native/sun/font/layout/CursiveAttachmentSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/CursiveAttachmentSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -51,23 +51,27 @@
     }
 
     LEPoint entryAnchor, exitAnchor;
-    Offset entryOffset = SWAPW(entryExitRecords[coverageIndex].entryAnchor); // TODO
+    Offset entryOffset = SWAPW(entryExitRecords[coverageIndex].entryAnchor);
     Offset exitOffset  = SWAPW(entryExitRecords[coverageIndex].exitAnchor);
 
     if (entryOffset != 0) {
-        const AnchorTable *entryAnchorTable = (const AnchorTable *) ((char *) this + entryOffset);
+        LEReferenceTo<AnchorTable> entryAnchorTable(base, success, entryOffset);
 
-        entryAnchorTable->getAnchor(glyphID, fontInstance, entryAnchor);
-        glyphIterator->setCursiveEntryPoint(entryAnchor);
+        if( LE_SUCCESS(success) ) {
+          entryAnchorTable->getAnchor(entryAnchorTable, glyphID, fontInstance, entryAnchor, success);
+          glyphIterator->setCursiveEntryPoint(entryAnchor);
+        }
     } else {
         //glyphIterator->clearCursiveEntryPoint();
     }
 
     if (exitOffset != 0) {
-        const AnchorTable *exitAnchorTable = (const AnchorTable *) ((char *) this + exitOffset);
+        LEReferenceTo<AnchorTable> exitAnchorTable(base, success, exitOffset);
 
-        exitAnchorTable->getAnchor(glyphID, fontInstance, exitAnchor);
-        glyphIterator->setCursiveExitPoint(exitAnchor);
+        if( LE_SUCCESS(success) ) {
+          exitAnchorTable->getAnchor(exitAnchorTable, glyphID, fontInstance, exitAnchor, success);
+          glyphIterator->setCursiveExitPoint(exitAnchor);
+        }
     } else {
         //glyphIterator->clearCursiveExitPoint();
     }
--- a/jdk/src/share/native/sun/font/layout/DeviceTables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/DeviceTables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -43,7 +43,7 @@
 
 #define FORMAT_COUNT LE_ARRAY_SIZE(fieldBits)
 
-le_int16 DeviceTable::getAdjustment(le_uint16 ppem) const
+le_int16 DeviceTable::getAdjustment(const LEReferenceTo<DeviceTable>&base, le_uint16 ppem, LEErrorCode &success) const
 {
     le_uint16 start = SWAPW(startSize);
     le_uint16 format = SWAPW(deltaFormat) - 1;
@@ -53,6 +53,13 @@
         le_uint16 sizeIndex = ppem - start;
         le_uint16 bits = fieldBits[format];
         le_uint16 count = 16 / bits;
+
+        LEReferenceToArrayOf<le_uint16> deltaValuesRef(base, success, deltaValues, (sizeIndex / count));
+
+        if(LE_FAILURE(success)) {
+          return result;
+        }
+
         le_uint16 word = SWAPW(deltaValues[sizeIndex / count]);
         le_uint16 fieldIndex = sizeIndex % count;
         le_uint16 shift = 16 - (bits * (fieldIndex + 1));
--- a/jdk/src/share/native/sun/font/layout/DeviceTables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/DeviceTables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -50,7 +50,7 @@
     le_uint16  deltaFormat;
     le_uint16  deltaValues[ANY_NUMBER];
 
-    le_int16   getAdjustment(le_uint16 ppem) const;
+    le_int16   getAdjustment(const LEReferenceTo<DeviceTable> &base, le_uint16 ppem, LEErrorCode &success) const;
 
 private:
     static const le_uint16 fieldMasks[];
--- a/jdk/src/share/native/sun/font/layout/ExtensionSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ExtensionSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -48,7 +48,6 @@
                                      const LookupProcessor *lookupProcessor, le_uint16 lookupType,
                                       GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const
 {
-
     if (LE_FAILURE(success)) {
         return 0;
     }
--- a/jdk/src/share/native/sun/font/layout/ExtensionSubtables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ExtensionSubtables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -52,8 +52,7 @@
     le_uint16 extensionLookupType;
     le_uint32 extensionOffset;
 
-    le_uint32 process(const LEReferenceTo<ExtensionSubtable> &extRef,
-                      const LookupProcessor *lookupProcessor, le_uint16 lookupType,
+    le_uint32 process(const LEReferenceTo<ExtensionSubtable> &base, const LookupProcessor *lookupProcessor, le_uint16 lookupType,
                       GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode& success) const;
 };
 
--- a/jdk/src/share/native/sun/font/layout/GDEFMarkFilter.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/GDEFMarkFilter.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -49,11 +49,11 @@
     // nothing to do?
 }
 
-le_bool GDEFMarkFilter::accept(LEGlyphID glyph) const
+le_bool GDEFMarkFilter::accept(LEGlyphID glyph, LEErrorCode &success) const
 {
-    le_int32 glyphClass = classDefTable->getGlyphClass(glyph);
+  le_int32 glyphClass = classDefTable->getGlyphClass(classDefTable, glyph, success);
 
-    return glyphClass == gcdMarkGlyph;
+  return glyphClass == gcdMarkGlyph;
 }
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/GDEFMarkFilter.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/GDEFMarkFilter.h	Fri Jan 10 15:04:46 2014 +0000
@@ -55,7 +55,7 @@
     GDEFMarkFilter(const LEReferenceTo<GlyphDefinitionTableHeader> &gdefTable, LEErrorCode &success);
     virtual ~GDEFMarkFilter();
 
-    virtual le_bool accept(LEGlyphID glyph) const;
+    virtual le_bool accept(LEGlyphID glyph, LEErrorCode &success) const;
 };
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/GlyphIterator.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/GlyphIterator.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -41,14 +41,13 @@
 U_NAMESPACE_BEGIN
 
 GlyphIterator::GlyphIterator(LEGlyphStorage &theGlyphStorage, GlyphPositionAdjustments *theGlyphPositionAdjustments, le_bool rightToLeft, le_uint16 theLookupFlags,
-                             FeatureMask theFeatureMask, const LEReferenceTo<GlyphDefinitionTableHeader> &theGlyphDefinitionTableHeader)
+                             FeatureMask theFeatureMask, const LEReferenceTo<GlyphDefinitionTableHeader> &theGlyphDefinitionTableHeader, LEErrorCode &success)
   : direction(1), position(-1), nextLimit(-1), prevLimit(-1),
     glyphStorage(theGlyphStorage), glyphPositionAdjustments(theGlyphPositionAdjustments),
     srcIndex(-1), destIndex(-1), lookupFlags(theLookupFlags), featureMask(theFeatureMask), glyphGroup(0),
     glyphClassDefinitionTable(), markAttachClassDefinitionTable()
 
 {
-  LEErrorCode success = LE_NO_ERROR; // TODO
     le_int32 glyphCount = glyphStorage.getGlyphCount();
 
     if (theGlyphDefinitionTableHeader.isValid()) {
@@ -388,7 +387,7 @@
 
 void GlyphIterator::filterResetCache(void) {
   filterCacheValid = FALSE;
-    }
+}
 
 le_bool GlyphIterator::filterGlyph(le_uint32 index)
 {
@@ -399,53 +398,53 @@
 
       le_bool &filterResult = filterCache.result;  // NB: Making this a reference to accept the updated value, in case
                                                // we want more fancy cacheing in the future.
-    if (LE_GET_GLYPH(glyphID) >= 0xFFFE) {
+      if (LE_GET_GLYPH(glyphID) >= 0xFFFE) {
         filterResult = TRUE;
       } else {
         LEErrorCode success = LE_NO_ERROR;
         le_int32 glyphClass = gcdNoGlyphClass;
-    if (glyphClassDefinitionTable.isValid()) {
-      glyphClass = glyphClassDefinitionTable->getGlyphClass(glyphClassDefinitionTable, glyphID, success);
-    }
+        if (glyphClassDefinitionTable.isValid()) {
+          glyphClass = glyphClassDefinitionTable->getGlyphClass(glyphClassDefinitionTable, glyphID, success);
+        }
         switch (glyphClass) {
-    case gcdNoGlyphClass:
+        case gcdNoGlyphClass:
           filterResult = FALSE;
           break;
 
-    case gcdSimpleGlyph:
+        case gcdSimpleGlyph:
           filterResult = (lookupFlags & lfIgnoreBaseGlyphs) != 0;
           break;
 
-    case gcdLigatureGlyph:
+        case gcdLigatureGlyph:
           filterResult = (lookupFlags & lfIgnoreLigatures) != 0;
           break;
 
-    case gcdMarkGlyph:
-        if ((lookupFlags & lfIgnoreMarks) != 0) {
+        case gcdMarkGlyph:
+          if ((lookupFlags & lfIgnoreMarks) != 0) {
             filterResult = TRUE;
           } else {
-        le_uint16 markAttachType = (lookupFlags & lfMarkAttachTypeMask) >> lfMarkAttachTypeShift;
+            le_uint16 markAttachType = (lookupFlags & lfMarkAttachTypeMask) >> lfMarkAttachTypeShift;
 
-        if ((markAttachType != 0) && (markAttachClassDefinitionTable.isValid())) {
+            if ((markAttachType != 0) && (markAttachClassDefinitionTable.isValid())) {
               filterResult = (markAttachClassDefinitionTable
                           -> getGlyphClass(markAttachClassDefinitionTable, glyphID, success) != markAttachType);
             } else {
               filterResult = FALSE;
-        }
-    }
+            }
+          }
           break;
 
-    case gcdComponentGlyph:
+        case gcdComponentGlyph:
           filterResult = ((lookupFlags & lfIgnoreBaseGlyphs) != 0);
           break;
 
-    default:
+        default:
           filterResult = FALSE;
           break;
-    }
+        }
       }
       filterCacheValid = TRUE;
-        }
+    }
 
     return filterCache.result;
 }
--- a/jdk/src/share/native/sun/font/layout/GlyphIterator.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/GlyphIterator.h	Fri Jan 10 15:04:46 2014 +0000
@@ -49,7 +49,7 @@
 class GlyphIterator : public UMemory {
 public:
     GlyphIterator(LEGlyphStorage &theGlyphStorage, GlyphPositionAdjustments *theGlyphPositionAdjustments, le_bool rightToLeft, le_uint16 theLookupFlags,
-                  FeatureMask theFeatureMask, const LEReferenceTo<GlyphDefinitionTableHeader> &theGlyphDefinitionTableHeader);
+                  FeatureMask theFeatureMask, const LEReferenceTo<GlyphDefinitionTableHeader> &theGlyphDefinitionTableHeader, LEErrorCode &success);
 
     GlyphIterator(GlyphIterator &that);
 
--- a/jdk/src/share/native/sun/font/layout/GlyphPosnLookupProc.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/GlyphPosnLookupProc.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -95,6 +95,8 @@
 
     le_uint32 delta = 0;
 
+    //_LETRACE("attempting lookupType #%d", lookupType);
+
     switch(lookupType)
     {
     case 0:
@@ -152,21 +154,21 @@
     {
         LEReferenceTo<ContextualPositioningSubtable> subtable(lookupSubtable, success);
 
-        delta = subtable->process(this, glyphIterator, fontInstance, success);
+        delta = subtable->process(subtable, this , glyphIterator, fontInstance, success);
         break;
     }
 
     case gpstChainedContext:
     {
-        LEReferenceTo<ChainingContextualPositioningSubtable> subtable(lookupSubtable, success);
+        const LEReferenceTo<ChainingContextualPositioningSubtable> subtable(lookupSubtable, success);
 
-        delta = subtable->process(this, glyphIterator, fontInstance, success);
+        delta = subtable->process(subtable, this, glyphIterator, fontInstance, success);
         break;
     }
 
     case gpstExtension:
     {
-        LEReferenceTo<ExtensionSubtable> subtable(lookupSubtable, success);
+        const LEReferenceTo<ExtensionSubtable> subtable(lookupSubtable, success);
 
         delta = subtable->process(subtable, this, lookupType, glyphIterator, fontInstance, success);
         break;
@@ -176,6 +178,12 @@
         break;
     }
 
+#if LE_TRACE
+    if(delta != 0) {
+      _LETRACE("GlyphPositioningLookupProcessor applied #%d -> delta %d @ %d", lookupType, delta, glyphIterator->getCurrStreamPosition());
+    }
+#endif
+
     return delta;
 }
 
--- a/jdk/src/share/native/sun/font/layout/GlyphSubstLookupProc.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/GlyphSubstLookupProc.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -123,7 +123,7 @@
     {
         const LEReferenceTo<ContextualSubstitutionSubtable> subtable(lookupSubtable, success);
 
-        delta = subtable->process(this, glyphIterator, fontInstance, success);
+        delta = subtable->process(subtable, this, glyphIterator, fontInstance, success);
         break;
     }
 
@@ -131,7 +131,7 @@
     {
         const LEReferenceTo<ChainingContextualSubstitutionSubtable> subtable(lookupSubtable, success);
 
-        delta = subtable->process(this, glyphIterator, fontInstance, success);
+        delta = subtable->process(subtable, this, glyphIterator, fontInstance, success);
         break;
     }
 
--- a/jdk/src/share/native/sun/font/layout/IndicLayoutEngine.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/IndicLayoutEngine.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -44,7 +44,7 @@
 #include "LEGlyphStorage.h"
 
 #include "IndicReordering.h"
-#include <stdio.h>
+
 U_NAMESPACE_BEGIN
 
 UOBJECT_DEFINE_RTTI_IMPLEMENTATION(IndicOpenTypeLayoutEngine)
@@ -53,14 +53,14 @@
                                                      le_int32 typoFlags, le_bool version2, const LEReferenceTo<GlyphSubstitutionTableHeader> &gsubTable, LEErrorCode &success)
     : OpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, gsubTable, success), fMPreFixups(NULL)
 {
-        if ( version2 ) {
-                fFeatureMap = IndicReordering::getv2FeatureMap(fFeatureMapCount);
-        } else {
+  if ( version2 ) {
+    fFeatureMap = IndicReordering::getv2FeatureMap(fFeatureMapCount);
+  } else {
     fFeatureMap = IndicReordering::getFeatureMap(fFeatureMapCount);
-        }
-    fFeatureOrder = TRUE;
-    fVersion2 = version2;
-    fFilterZeroWidth = IndicReordering::getFilterZeroWidth(fScriptCode);
+  }
+  fFeatureOrder = TRUE;
+  fVersion2 = version2;
+  fFilterZeroWidth = IndicReordering::getFilterZeroWidth(fScriptCode);
 }
 
 IndicOpenTypeLayoutEngine::IndicOpenTypeLayoutEngine(const LEFontInstance *fontInstance, le_int32 scriptCode, le_int32 languageCode, le_int32 typoFlags, LEErrorCode &success)
@@ -68,7 +68,7 @@
 {
     fFeatureMap = IndicReordering::getFeatureMap(fFeatureMapCount);
     fFeatureOrder = TRUE;
-        fVersion2 =  FALSE;
+    fVersion2 =  FALSE;
 }
 
 IndicOpenTypeLayoutEngine::~IndicOpenTypeLayoutEngine()
@@ -90,6 +90,7 @@
         return 0;
     }
 
+    _LETRACE("IOTLE::gp, calling parent");
     le_int32 retCount = OpenTypeLayoutEngine::glyphProcessing(chars, offset, count, max, rightToLeft, glyphStorage, success);
 
     if (LE_FAILURE(success)) {
@@ -97,11 +98,15 @@
     }
 
     if (fVersion2) {
-        IndicReordering::finalReordering(glyphStorage,retCount);
-        IndicReordering::applyPresentationForms(glyphStorage,retCount);
-        OpenTypeLayoutEngine::glyphSubstitution(count,max, rightToLeft, glyphStorage, success);
+      _LETRACE("IOTLE::gp, v2 final,");
+      IndicReordering::finalReordering(glyphStorage,retCount);
+      _LETRACE("IOTLE::gp, v2 pres");
+      IndicReordering::applyPresentationForms(glyphStorage,retCount);
+      _LETRACE("IOTLE::gp, parent gsub");
+      OpenTypeLayoutEngine::glyphSubstitution(count,max, rightToLeft, glyphStorage, success);
     } else {
-        IndicReordering::adjustMPres(fMPreFixups, glyphStorage, success);
+      _LETRACE("IOTLE::gp, adjust mpres");
+      IndicReordering::adjustMPres(fMPreFixups, glyphStorage, success);
     }
     return retCount;
 }
@@ -116,6 +121,8 @@
         return 0;
     }
 
+    _LETRACE("IOTLE: charProc");
+
     if (chars == NULL || offset < 0 || count < 0 || max < 0 || offset >= max || offset + count > max) {
         success = LE_ILLEGAL_ARGUMENT_ERROR;
         return 0;
@@ -143,8 +150,10 @@
 
     le_int32 outCharCount;
     if (fVersion2) {
+        _LETRACE("v2process");
         outCharCount = IndicReordering::v2process(&chars[offset], count, fScriptCode, outChars, glyphStorage);
     } else {
+        _LETRACE("reorder");
         outCharCount = IndicReordering::reorder(&chars[offset], count, fScriptCode, outChars, glyphStorage, &fMPreFixups, success);
     }
 
--- a/jdk/src/share/native/sun/font/layout/IndicReordering.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/IndicReordering.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -254,8 +254,8 @@
         return fGlyphStorage.getAuxData(charIndex,success);
     }
 
-        void decomposeReorderMatras ( const IndicClassTable *classTable, le_int32 beginSyllable, le_int32 nextSyllable, le_int32 inv_count ) {
-                le_int32 i;
+    void decomposeReorderMatras ( const IndicClassTable *classTable, le_int32 beginSyllable, le_int32 nextSyllable, le_int32 inv_count ) {
+        le_int32 i;
         LEErrorCode success = LE_NO_ERROR;
 
                 for ( i = beginSyllable ; i < nextSyllable ; i++ ) {
--- a/jdk/src/share/native/sun/font/layout/KernTable.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/KernTable.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -39,7 +39,7 @@
 
 #include <stdio.h>
 
-#define DEBUG 0
+#define DEBUG_KERN_TABLE 0
 
 U_NAMESPACE_BEGIN
 
@@ -99,14 +99,14 @@
   : pairsSwapped(NULL), fTable(base)
 {
   if(LE_FAILURE(success) || (fTable.isEmpty())) {
-#if DEBUG
+#if DEBUG_KERN_TABLE
     fprintf(stderr, "no kern data\n");
 #endif
     return;
   }
   LEReferenceTo<KernTableHeader> header(fTable, success);
 
-#if DEBUG
+#if DEBUG_KERN_TABLE
   // dump first 32 bytes of header
   for (int i = 0; i < 64; ++i) {
     fprintf(stderr, "%0.2x ", ((const char*)header.getAlias())[i]&0xff);
@@ -171,13 +171,13 @@
         fprintf(stderr, "  searchRange: %d entrySelector: %d rangeShift: %d\n", searchRange, entrySelector, rangeShift);
         fprintf(stderr, "[[ ignored font table entries: range %d selector %d shift %d ]]\n", SWAPW(table->searchRange), SWAPW(table->entrySelector), SWAPW(table->rangeShift));
 #endif
-#if DEBUG
+#if DEBUG_KERN_TABLE
         fprintf(stderr, "coverage: %0.4x nPairs: %d pairs 0x%x\n", coverage, nPairs, pairsSwapped);
         fprintf(stderr,
           "  searchRange(pairs): %d entrySelector: %d rangeShift(pairs): %d\n",
           searchRange, entrySelector, rangeShift);
 
-        {
+        if (LE_SUCCESS(success)) {
           // dump part of the pair list
           char ids[256];
           for (int i = 256; --i >= 0;) {
@@ -242,7 +242,7 @@
         p = tp;
       }
 
-#if DEBUG
+#if DEBUG_KERN_TABLE
       fprintf(stderr, "binary search for %0.8x\n", key);
 #endif
 
@@ -251,13 +251,13 @@
         probe >>= 1;
         tp = (const PairInfo*)(p + (probe/KERN_PAIRINFO_SIZE));
         le_uint32 tkey = tp->key;
-#if DEBUG
+#if DEBUG_KERN_TABLE
         fprintf(stdout, "   %.3d (%0.8x)\n", (tp - pairsSwapped), tkey);
 #endif
         if (tkey <= key) {
           if (tkey == key) {
             le_int16 value = SWAPW(tp->value);
-#if DEBUG
+#if DEBUG_KERN_TABLE
             fprintf(stdout, "binary found kerning pair %x:%x at %d, value: 0x%x (%g)\n",
                     storage[i-1], storage[i], i, value & 0xffff, font->xUnitsToPoints(value));
             fflush(stdout);
--- a/jdk/src/share/native/sun/font/layout/LEFontInstance.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LEFontInstance.h	Fri Jan 10 15:04:46 2014 +0000
@@ -181,6 +181,10 @@
      *
      * Subclasses which represent composite fonts should always return <code>NULL</code>.
      *
+     * Note that implementing this function does not allow for range checking.
+     * Subclasses that desire the safety of range checking must implement the
+     * variation which has a length parameter.
+     *
      * @param tableTag - the four byte table tag. (e.g. 'cmap')
      *
      * @return the address of the table in memory, or <code>NULL</code>
@@ -200,6 +204,8 @@
      * Subclasses which represent composite fonts should always return <code>NULL</code>.
      *
      * This version sets a length, for range checking.
+     * Note that range checking can only be accomplished if this function is
+     * implemented in subclasses.
      *
      * @param tableTag - the four byte table tag. (e.g. 'cmap')
      * @param length - ignored on entry, on exit will be the length of the table if known, or -1 if unknown.
@@ -572,5 +578,3 @@
 
 U_NAMESPACE_END
 #endif
-
-
--- a/jdk/src/share/native/sun/font/layout/LEGlyphFilter.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LEGlyphFilter.h	Fri Jan 10 15:04:46 2014 +0000
@@ -62,7 +62,7 @@
      *
      * @internal
      */
-    virtual le_bool accept(LEGlyphID glyph) const = 0;
+    virtual le_bool accept(LEGlyphID glyph, LEErrorCode &success) const = 0;
 };
 #endif  /* U_HIDE_INTERNAL_API */
 
--- a/jdk/src/share/native/sun/font/layout/LEGlyphStorage.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LEGlyphStorage.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -458,7 +458,7 @@
       success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
       return;
     }
-
+    _LETRACE("set%-4d\t(%.2f, %.2f)", glyphIndex, x, y);
     fPositions[glyphIndex * 2]     = x;
     fPositions[glyphIndex * 2 + 1] = y;
 }
@@ -688,10 +688,9 @@
 
     // the source glyph we're pointing at
     // just got replaced by the insertion
-        fSrcIndex -= 1;
+    fSrcIndex -= 1;
 
     return FALSE;
 }
 
 U_NAMESPACE_END
-
--- a/jdk/src/share/native/sun/font/layout/LEGlyphStorage.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LEGlyphStorage.h	Fri Jan 10 15:04:46 2014 +0000
@@ -568,4 +568,3 @@
 
 U_NAMESPACE_END
 #endif
-
--- a/jdk/src/share/native/sun/font/layout/LEScripts.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LEScripts.h	Fri Jan 10 15:04:46 2014 +0000
@@ -30,7 +30,7 @@
  * WARNING: THIS FILE IS MACHINE GENERATED. DO NOT HAND EDIT IT UNLESS
  * YOU REALLY KNOW WHAT YOU'RE DOING.
  *
- * Generated on: 10/26/2010 02:53:33 PM PDT
+ * Generated on: 11/01/2011 04:08:09 PM PDT
  */
 
 #ifndef __LESCRIPTS_H
@@ -262,7 +262,16 @@
     khojScriptCode = 157,
     tirhScriptCode = 158,
 
-    scriptCodeCount = 159
+/**
+ * @stable ICU 52
+ */
+    aghbScriptCode = 159,
+    mahjScriptCode = 160,
+
+/**
+ * @stable ICU 2.2
+ */
+    scriptCodeCount
 };
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/LEStandalone.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LEStandalone.h	Fri Jan 10 15:04:46 2014 +0000
@@ -132,6 +132,9 @@
 #define uprv_memcpy memcpy
 #define uprv_realloc realloc
 
+#define U_EXPORT2
+#define U_CAPI extern "C"
+
 #if !defined(U_IS_BIG_ENDIAN)
     #ifdef _LITTLE_ENDIAN
         #define U_IS_BIG_ENDIAN 0
--- a/jdk/src/share/native/sun/font/layout/LETableReference.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LETableReference.h	Fri Jan 10 15:04:46 2014 +0000
@@ -37,34 +37,47 @@
 #include "LETypes.h"
 #include "LEFontInstance.h"
 
+/**
+ * \def LE_ENABLE_RAW
+ * If this is 1, enables old non-safe raw access
+ */
+#ifndef LE_ENABLE_RAW
+#define LE_ENABLE_RAW 0
+#endif
 
-#define kQuestionmarkTableTag  0x3F3F3F3FUL
-#define kTildeTableTag  0x7e7e7e7eUL
+#define kQuestionmarkTableTag  0x3F3F3F3FUL /* ???? */
+#define kStaticTableTag  0x30303030UL  /* 0000 */
+#define kTildeTableTag  0x7e7e7e7eUL /* ~~~~ */
 #ifdef __cplusplus
 
 // internal - interface for range checking
 U_NAMESPACE_BEGIN
 
 #if LE_ASSERT_BAD_FONT
+
+#ifndef LE_TRACE_TR
+#define LE_TRACE_TR 0
+#endif
+
 class LETableReference; // fwd
 /**
  *  defined in OpenTypeUtilities.cpp
  * @internal
  */
-extern void _debug_LETableReference(const char *f, int l, const char *msg, const LETableReference *what, const void *ptr, size_t len);
+U_CAPI void U_EXPORT2 _debug_LETableReference(const char *f, int l, const char *msg, const LETableReference *what, const void *ptr, size_t len);
 
 #define LE_DEBUG_TR(x) _debug_LETableReference(__FILE__, __LINE__, x, this, NULL, 0);
 #define LE_DEBUG_TR3(x,y,z) _debug_LETableReference(__FILE__, __LINE__, x, this, (const void*)y, (size_t)z);
-#if 0
-#define LE_TRACE_TR(x) _debug_LETableReference(__FILE__, __LINE__, x, this, NULL, 0);
+#if LE_TRACE_TR
+#define _TRTRACE(x) _debug_LETableReference(__FILE__, __LINE__, x, this, NULL, 0);
 #else
-#define LE_TRACE_TR(x)
+#define _TRTRACE(x)
 #endif
 
 #else
 #define LE_DEBUG_TR(x)
 #define LE_DEBUG_TR3(x,y,z)
-#define LE_TRACE_TR(x)
+#define _TRTRACE(x)
 #endif
 
 /**
@@ -72,6 +85,13 @@
  */
 class LETableReference {
 public:
+
+  /**
+   * Dummy enum asserting that a value is actually static data
+   * and does not need to be range checked
+   */
+  enum EStaticData { kStaticData = 0 };
+
 /**
  * @internal
  * Construct from a specific tag
@@ -79,28 +99,42 @@
   LETableReference(const LEFontInstance* font, LETag tableTag, LEErrorCode &success) :
     fFont(font), fTag(tableTag), fParent(NULL), fStart(NULL),fLength(LE_UINTPTR_MAX) {
       loadTable(success);
-    LE_TRACE_TR("INFO: new table load")
+    _TRTRACE("INFO: new table load")
   }
 
   LETableReference(const LETableReference &parent, LEErrorCode &success) : fFont(parent.fFont), fTag(parent.fTag), fParent(&parent), fStart(parent.fStart), fLength(parent.fLength) {
     if(LE_FAILURE(success)) {
       clear();
     }
-    LE_TRACE_TR("INFO: new clone")
+    _TRTRACE("INFO: new clone")
   }
 
+#if LE_ENABLE_RAW
+   /**
+    * Construct  without a parent LETR.
+    */
    LETableReference(const le_uint8* data, size_t length = LE_UINTPTR_MAX) :
     fFont(NULL), fTag(kQuestionmarkTableTag), fParent(NULL), fStart(data), fLength(length) {
-    LE_TRACE_TR("INFO: new raw")
+    _TRTRACE("INFO: new raw")
   }
+#endif
+
+   /**
+    * Construct  without a parent LETR.
+    */
+ LETableReference(EStaticData /* NOTUSED */, const le_uint8* data, size_t length) :
+    fFont(NULL), fTag(kQuestionmarkTableTag), fParent(NULL), fStart(data), fLength(length) {
+    _TRTRACE("INFO: new EStaticData")
+  }
+
   LETableReference() :
     fFont(NULL), fTag(kQuestionmarkTableTag), fParent(NULL), fStart(NULL), fLength(0) {
-    LE_TRACE_TR("INFO: new empty")
+    _TRTRACE("INFO: new empty")
   }
 
   ~LETableReference() {
-    fTag=kTildeTableTag;
-    LE_TRACE_TR("INFO: new dtor")
+    fTag= (LETag)kTildeTableTag;
+    _TRTRACE("INFO: new dtor")
   }
 
   /**
@@ -126,7 +160,7 @@
           fLength = (fParent->fLength) - offset; // decrement length as base address is incremented
         }
         if(fLength != LE_UINTPTR_MAX) {  // if we have bounds:
-          if(offset+fLength > fParent->fLength) {
+          if((offset+fLength < offset) || (offset+fLength > fParent->fLength)) {
             LE_DEBUG_TR3("offset+fLength out of range: (%p) +%d", NULL, offset+fLength);
             err = LE_INDEX_OUT_OF_BOUNDS_ERROR; // exceeded
             clear();
@@ -136,11 +170,13 @@
     } else {
       clear();
     }
-    LE_TRACE_TR("INFO: new subset")
+    _TRTRACE("INFO: new subset")
   }
 
   const void* getAlias() const { return (const void*)fStart; }
-  const void* getAliasTODO() const { LE_DEBUG_TR("getAliasTODO()"); return (const void*)fStart; }
+#ifndef LE_ENABLE_RAW
+  const void* getAliasRAW() const { LE_DEBUG_TR("getAliasRAW()"); return (const void*)fStart; }
+#endif
   le_bool isEmpty() const { return fStart==NULL || fLength==0; }
   le_bool isValid() const { return !isEmpty(); }
   le_bool hasBounds() const { return fLength!=LE_UINTPTR_MAX; }
@@ -233,7 +269,18 @@
 
   void setRaw(const void *data, size_t length = LE_UINTPTR_MAX) {
     fFont = NULL;
-    fTag = kQuestionmarkTableTag;
+    fTag = (LETag)kQuestionmarkTableTag;
+    fParent = NULL;
+    fStart = (const le_uint8*)data;
+    fLength = length;
+  }
+
+  /**
+   * set this object pointing to static data
+   */
+  void setTo(EStaticData /*notused*/, const void *data, size_t length) {
+    fFont = NULL;
+    fTag = (LETag)kStaticTableTag;
     fParent = NULL;
     fStart = (const le_uint8*)data;
     fLength = length;
@@ -276,97 +323,6 @@
  * Open a new entry based on an existing table
  */
 
-/**
- * \def LE_UNBOUNDED_ARRAY
- * define an array with no *known* bound. Will trim to available size.
- * @internal
- */
-#define LE_UNBOUNDED_ARRAY LE_UINT32_MAX
-
-template<class T>
-class LEReferenceToArrayOf : public LETableReference {
-public:
-  LEReferenceToArrayOf(const LETableReference &parent, LEErrorCode &success, size_t offset, le_uint32 count)
-    : LETableReference(parent, offset, LE_UINTPTR_MAX, success), fCount(count) {
-    LE_TRACE_TR("INFO: new RTAO by offset")
-    if(LE_SUCCESS(success)) {
-      if(count == LE_UNBOUNDED_ARRAY) { // not a known length
-        count = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
-      }
-      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*count, success);
-    }
-    if(LE_FAILURE(success)) {
-      fCount=0;
-      clear();
-    }
-  }
-
-  LEReferenceToArrayOf(const LETableReference &parent, LEErrorCode &success, const T* array, le_uint32 count)
-    : LETableReference(parent, parent.ptrToOffset(array, success), LE_UINTPTR_MAX, success), fCount(count) {
-LE_TRACE_TR("INFO: new RTAO")
-    if(LE_SUCCESS(success)) {
-      if(count == LE_UNBOUNDED_ARRAY) { // not a known length
-        count = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
-      }
-      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*count, success);
-    }
-    if(LE_FAILURE(success)) clear();
-  }
- LEReferenceToArrayOf(const LETableReference &parent, LEErrorCode &success, const T* array, size_t offset, le_uint32 count)
-   : LETableReference(parent, parent.ptrToOffset(array, success)+offset, LE_UINTPTR_MAX, success), fCount(count) {
-LE_TRACE_TR("INFO: new RTAO")
-    if(LE_SUCCESS(success)) {
-      if(count == LE_UNBOUNDED_ARRAY) { // not a known length
-        count = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
-      }
-      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*count, success);
-    }
-    if(LE_FAILURE(success)) clear();
-  }
-
- LEReferenceToArrayOf() :LETableReference(), fCount(0) {}
-
-  le_uint32 getCount() const { return fCount; }
-
-  using LETableReference::getAlias;
-
-  const T *getAlias(le_uint32 i, LEErrorCode &success) const {
-    return ((const T*)(((const char*)getAlias())+getOffsetFor(i, success)));
-  }
-
-  const T *getAliasTODO() const { LE_DEBUG_TR("getAliasTODO<>"); return (const T*)fStart; }
-
-  const T& getObject(le_uint32 i, LEErrorCode &success) const {
-    return *getAlias(i,success);
-  }
-
-  const T& operator()(le_uint32 i, LEErrorCode &success) const {
-    return *getAlias(i,success);
-  }
-
-  size_t getOffsetFor(le_uint32 i, LEErrorCode &success) const {
-    if(LE_SUCCESS(success)&&i<getCount()) {
-      return LETableVarSizer<T>::getSize()*i;
-    } else {
-      success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
-    }
-    return 0;
-  }
-
-  LEReferenceToArrayOf<T> &reparent(const LETableReference &base) {
-    fParent = &base;
-    return *this;
-  }
-
- LEReferenceToArrayOf(const LETableReference& parent, LEErrorCode & success) : LETableReference(parent,0, LE_UINTPTR_MAX, success), fCount(0) {
-    LE_TRACE_TR("INFO: null RTAO")
-  }
-
-private:
-  le_uint32 fCount;
-};
-
-
 template<class T>
 class LEReferenceTo : public LETableReference {
 public:
@@ -404,14 +360,26 @@
     verifyLength(0, LETableVarSizer<T>::getSize(), success);
     if(LE_FAILURE(success)) clear();
   }
+#if LE_ENABLE_RAW
  inline LEReferenceTo(const le_uint8 *data, size_t length = LE_UINTPTR_MAX) : LETableReference(data, length) {}
  inline LEReferenceTo(const T *data, size_t length = LE_UINTPTR_MAX) : LETableReference((const le_uint8*)data, length) {}
- inline LEReferenceTo() : LETableReference(NULL) {}
+#endif
+ inline LEReferenceTo(EStaticData staticData, const le_uint8 *data, size_t length) : LETableReference(staticData, data, length) {}
+ inline LEReferenceTo(EStaticData staticData, const T *data, size_t length) : LETableReference(staticData, (const le_uint8*)data, length) {}
 
+ inline LEReferenceTo() : LETableReference() {}
+
+#if LE_ENABLE_RAW
  inline LEReferenceTo<T>& operator=(const T* other) {
     setRaw(other);
     return *this;
   }
+#endif
+
+ LEReferenceTo<T>& setTo(LETableReference::EStaticData staticData, const T* other, size_t length) {
+   LETableReference::setTo(staticData, other, length);
+   return *this;
+ }
 
   LEReferenceTo<T> &reparent(const LETableReference &base) {
     fParent = &base;
@@ -430,11 +398,135 @@
   }
 
   const T *operator->() const { return getAlias(); }
+  const T *operator*() const { return getAlias(); }
   const T *getAlias() const { return (const T*)fStart; }
-  const T *getAliasTODO() const { LE_DEBUG_TR("getAliasTODO<>"); return (const T*)fStart; }
+#if LE_ENABLE_RAW
+  const T *getAliasRAW() const { LE_DEBUG_TR("getAliasRAW<>"); return (const T*)fStart; }
+#endif
+
 };
 
 
+/**
+ * \def LE_UNBOUNDED_ARRAY
+ * define an array with no *known* bound. Will trim to available size.
+ * @internal
+ */
+#define LE_UNBOUNDED_ARRAY LE_UINT32_MAX
+
+template<class T>
+class LEReferenceToArrayOf : public LETableReference {
+public:
+  LEReferenceToArrayOf(const LETableReference &parent, LEErrorCode &success, size_t offset, le_uint32 count)
+    : LETableReference(parent, offset, LE_UINTPTR_MAX, success), fCount(count) {
+    _TRTRACE("INFO: new RTAO by offset")
+    if(LE_SUCCESS(success)) {
+      if(fCount == LE_UNBOUNDED_ARRAY) { // not a known length
+        fCount = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
+      }
+      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*fCount, success);
+    }
+    if(LE_FAILURE(success)) {
+      fCount=0;
+      clear();
+    }
+  }
+
+  LEReferenceToArrayOf(const LETableReference &parent, LEErrorCode &success, const T* array, le_uint32 count)
+    : LETableReference(parent, parent.ptrToOffset(array, success), LE_UINTPTR_MAX, success), fCount(count) {
+_TRTRACE("INFO: new RTAO")
+    if(LE_SUCCESS(success)) {
+      if(fCount == LE_UNBOUNDED_ARRAY) { // not a known length
+        fCount = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
+      }
+      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*fCount, success);
+    }
+    if(LE_FAILURE(success)) clear();
+  }
+ LEReferenceToArrayOf(const LETableReference &parent, LEErrorCode &success, const T* array, size_t offset, le_uint32 count)
+   : LETableReference(parent, parent.ptrToOffset(array, success)+offset, LE_UINTPTR_MAX, success), fCount(count) {
+_TRTRACE("INFO: new RTAO")
+    if(LE_SUCCESS(success)) {
+      if(fCount == LE_UNBOUNDED_ARRAY) { // not a known length
+        fCount = getLength()/LETableVarSizer<T>::getSize(); // fit to max size
+      }
+      LETableReference::verifyLength(0, LETableVarSizer<T>::getSize()*fCount, success);
+    }
+    if(LE_FAILURE(success)) clear();
+  }
+
+ LEReferenceToArrayOf() :LETableReference(), fCount(0) {}
+
+  le_uint32 getCount() const { return fCount; }
+
+  const T *getAlias() const { return (const T*)fStart; }
+
+  const T *getAlias(le_uint32 i, LEErrorCode &success) const {
+    return ((const T*)(((const char*)getAlias())+getOffsetFor(i, success)));
+  }
+
+#ifndef LE_ENABLE_RAW
+  const T *getAliasRAW() const { LE_DEBUG_TR("getAliasRAW<>"); return (const T*)fStart; }
+#endif
+
+  const T& getObject(le_uint32 i, LEErrorCode &success) const {
+    return *getAlias(i,success);
+  }
+
+  /**
+   * by-value array accessor for integral types.
+   */
+  const T operator[](le_uint32 i) const {
+    LEErrorCode success = LE_NO_ERROR;
+    const T *ret = getAlias(i, success);
+    if(LE_FAILURE(success) || ret==NULL) {
+#if LE_ASSERT_BAD_FONT
+      LE_DEBUG_TR3("Range error, out of bounds? (%p) #%d", NULL, i);
+#endif
+      return T(0); // will not work for all types.
+    }
+    return *ret;
+  }
+
+  const LEReferenceTo<T> getReference(le_uint32 i, LEErrorCode &success) const {
+    if(LE_FAILURE(success)) return LEReferenceTo<T>();
+    return LEReferenceTo<T>(*this, success, getAlias(i,success));
+  }
+
+  const T& operator()(le_uint32 i, LEErrorCode &success) const {
+    return *getAlias(i,success);
+  }
+
+  size_t getOffsetFor(le_uint32 i, LEErrorCode &success) const {
+    if(LE_SUCCESS(success)&&i<getCount()) {
+      return LETableVarSizer<T>::getSize()*i;
+    } else {
+      LE_DEBUG_TR3("getOffsetFor failed (%p) index=%d",NULL, i);
+      success = LE_INDEX_OUT_OF_BOUNDS_ERROR;
+    }
+    return 0;
+  }
+
+  LEReferenceToArrayOf<T> &reparent(const LETableReference &base) {
+    fParent = &base;
+    return *this;
+  }
+
+ LEReferenceToArrayOf(const LETableReference& parent, LEErrorCode & success) : LETableReference(parent,0, LE_UINTPTR_MAX, success), fCount(0) {
+    _TRTRACE("INFO: null RTAO")
+  }
+
+private:
+  le_uint32 fCount;
+};
+
+
+
+
+#ifdef _TRTRACE
+#undef _TRTRACE
+#endif
+
 U_NAMESPACE_END
 
 #endif
--- a/jdk/src/share/native/sun/font/layout/LETypes.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LETypes.h	Fri Jan 10 15:04:46 2014 +0000
@@ -337,6 +337,20 @@
 typedef struct LEPoint LEPoint;
 #endif
 
+/**
+ * \def LE_TRACE
+ * @internal
+ */
+#ifndef LE_TRACE
+# define LE_TRACE 0
+#endif
+
+#if LE_TRACE
+# include <stdio.h>
+# define _LETRACE printf("\n%s:%d: LE: ", __FILE__, __LINE__),printf
+#else
+# define _LETRACE 0&&
+#endif
 
 #ifndef U_HIDE_INTERNAL_API
 
@@ -553,7 +567,7 @@
     LE_CALT_FEATURE_TAG = 0x63616C74UL, /**< 'calt' */
     LE_CASE_FEATURE_TAG = 0x63617365UL, /**< 'case' */
     LE_CCMP_FEATURE_TAG = 0x63636D70UL, /**< 'ccmp' */
-        LE_CJCT_FEATURE_TAG = 0x636A6374UL, /**< 'cjct' */
+    LE_CJCT_FEATURE_TAG = 0x636A6374UL, /**< 'cjct' */
     LE_CLIG_FEATURE_TAG = 0x636C6967UL, /**< 'clig' */
     LE_CPSP_FEATURE_TAG = 0x63707370UL, /**< 'cpsp' */
     LE_CSWH_FEATURE_TAG = 0x63737768UL, /**< 'cswh' */
@@ -701,6 +715,12 @@
   LE_FEATURE_ENUM_MAX = LE_CHAR_FILTER_FEATURE_ENUM
 };
 
+
+/**
+ * Flags for typographic features.
+ * @internal
+ * @{
+ */
 #define LE_Kerning_FEATURE_FLAG   (1 << LE_Kerning_FEATURE_ENUM)
 #define LE_Ligatures_FEATURE_FLAG (1 << LE_Ligatures_FEATURE_ENUM)
 #define LE_NoCanon_FEATURE_FLAG (1 << LE_NoCanon_FEATURE_ENUM)
@@ -727,6 +747,9 @@
 #define LE_SS07_FEATURE_FLAG (1 << LE_SS07_FEATURE_ENUM)
 
 #define LE_CHAR_FILTER_FEATURE_FLAG (1 << LE_CHAR_FILTER_FEATURE_ENUM)
+/**
+ * @}
+ */
 
 #define LE_DEFAULT_FEATURE_FLAG (LE_Kerning_FEATURE_FLAG | LE_Ligatures_FEATURE_FLAG) /**< default features */
 
@@ -768,7 +791,7 @@
  *
  * @stable ICU 2.4
  */
-#ifndef LE_FAILURE
+#ifndef LE_SUCCESS
 #define LE_SUCCESS(code) (U_SUCCESS((UErrorCode)code))
 #endif
 
@@ -781,4 +804,4 @@
 #define LE_FAILURE(code) (U_FAILURE((UErrorCode)code))
 #endif
 
-#endif /* __LETYPES_H */
+#endif
--- a/jdk/src/share/native/sun/font/layout/LayoutEngine.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LayoutEngine.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -156,7 +156,7 @@
     CanonMarkFilter(const LEReferenceTo<GlyphDefinitionTableHeader> &gdefTable, LEErrorCode &success);
     virtual ~CanonMarkFilter();
 
-    virtual le_bool accept(LEGlyphID glyph) const;
+    virtual le_bool accept(LEGlyphID glyph, LEErrorCode &success) const;
 };
 
 CanonMarkFilter::CanonMarkFilter(const LEReferenceTo<GlyphDefinitionTableHeader> &gdefTable, LEErrorCode &success)
@@ -169,9 +169,8 @@
     // nothing to do?
 }
 
-le_bool CanonMarkFilter::accept(LEGlyphID glyph) const
+le_bool CanonMarkFilter::accept(LEGlyphID glyph, LEErrorCode &success) const
 {
-  LEErrorCode success = LE_NO_ERROR;
   le_int32 glyphClass = classDefTable->getGlyphClass(classDefTable, glyph, success);
   if(LE_FAILURE(success)) return false;
   return glyphClass != 0;
@@ -207,7 +206,7 @@
     fGlyphStorage = new LEGlyphStorage();
     if (fGlyphStorage == NULL) {
         success = LE_MEMORY_ALLOCATION_ERROR;
-}
+    }
 }
 
 le_int32 LayoutEngine::getGlyphCount() const
@@ -263,7 +262,9 @@
       return count;
     }
 
-    LEReferenceTo<GlyphSubstitutionTableHeader> canonGSUBTable((GlyphSubstitutionTableHeader *) CanonShaping::glyphSubstitutionTable);
+    LEReferenceTo<GlyphSubstitutionTableHeader> canonGSUBTable(LETableReference::kStaticData,
+                                                               (GlyphSubstitutionTableHeader *) CanonShaping::glyphSubstitutionTable,
+                                                               CanonShaping::glyphSubstitutionTableLen);
     LETag scriptTag  = OpenTypeLayoutEngine::getScriptTag(fScriptCode);
     LETag langSysTag = OpenTypeLayoutEngine::getLangSysTag(fLanguageCode);
     le_int32 i, dir = 1, out = 0, outCharCount = count;
@@ -300,7 +301,7 @@
 
           CanonShaping::reorderMarks(&chars[offset], count, rightToLeft, reordered, fakeGlyphStorage);
           inChars = reordered;
-                }
+        }
 
         fakeGlyphStorage.allocateAuxData(success);
 
@@ -323,7 +324,8 @@
           LE_DELETE_ARRAY(reordered);
         }
 
-        outCharCount = canonGSUBTable->process(canonGSUBTable, fakeGlyphStorage, rightToLeft, scriptTag, langSysTag, (const GlyphDefinitionTableHeader*)NULL, substitutionFilter, canonFeatureMap, canonFeatureMapCount, FALSE, success);
+        const LEReferenceTo<GlyphDefinitionTableHeader>  noGDEF; // empty gdef header
+        outCharCount = canonGSUBTable->process(canonGSUBTable, fakeGlyphStorage, rightToLeft, scriptTag, langSysTag, noGDEF, substitutionFilter, canonFeatureMap, canonFeatureMapCount, FALSE, success);
 
         if (LE_FAILURE(success)) {
             delete substitutionFilter;
@@ -403,10 +405,13 @@
         LEPoint advance;
 
         glyphStorage.setPosition(i, x, y, success);
+        _LETRACE("g#%-4d (%.2f, %.2f)", i, x, y);
 
         fFontInstance->getGlyphAdvance(glyphStorage[i], advance);
         x += advance.fX;
         y += advance.fY;
+
+
     }
 
     glyphStorage.setPosition(glyphCount, x, y, success);
@@ -424,7 +429,7 @@
         return;
     }
 
-    LEReferenceTo<GlyphDefinitionTableHeader> gdefTable((GlyphDefinitionTableHeader *) CanonShaping::glyphDefinitionTable,
+    LEReferenceTo<GlyphDefinitionTableHeader> gdefTable(LETableReference::kStaticData, (GlyphDefinitionTableHeader *) CanonShaping::glyphDefinitionTable,
                                                         CanonShaping::glyphDefinitionTableLen);
     CanonMarkFilter filter(gdefTable, success);
 
@@ -464,9 +469,10 @@
         glyphStorage.getGlyphPosition(p + 1, next, ignore, success);
 
         xAdvance = next - prev;
+        _LETRACE("p#%d (%.2f,%.2f)", p, xAdvance, 0);
         glyphStorage.adjustPosition(p, xAdjust, 0, success);
 
-        if (markFilter->accept(glyphStorage[p])) {
+        if (markFilter->accept(glyphStorage[p], success)) {
             xAdjust -= xAdvance;
         }
 
@@ -506,9 +512,13 @@
         glyphStorage.getGlyphPosition(p + 1, next, ignore, success);
 
         xAdvance = next - prev;
+
+        _LETRACE("p#%d (%.2f,%.2f)", p, xAdvance, 0);
+
+
         glyphStorage.adjustPosition(p, xAdjust, 0, success);
 
-        if (markFilter->accept(chars[c])) {
+        if (markFilter->accept(chars[c], success)) {
             xAdjust -= xAdvance;
         }
 
@@ -662,8 +672,10 @@
             break;
         }
     } else {
-        MorphTableHeader2 *morxTable = (MorphTableHeader2 *)fontInstance->getFontTable(morxTableTag);
-        if (morxTable != NULL && SWAPL(morxTable->version)==0x00020000) {
+        LEReferenceTo<MorphTableHeader2> morxTable(fontInstance, morxTableTag, success);
+        if (LE_SUCCESS(success) &&
+            morxTable.isValid() &&
+            SWAPL(morxTable->version)==0x00020000) {
             result = new GXLayoutEngine2(fontInstance, scriptCode, languageCode, morxTable, typoFlags, success);
         } else {
           LEReferenceTo<MorphTableHeader> mortTable(fontInstance, mortTableTag, success);
@@ -686,21 +698,20 @@
                         break;
                     }
 
-            case arabScriptCode:
-            //case hebrScriptCode:
-                result = new UnicodeArabicOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
-                break;
+                case arabScriptCode:
+                  result = new UnicodeArabicOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
+                  break;
 
-            //case hebrScriptCode:
-            //    return new HebrewOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags);
+                  //case hebrScriptCode:
+                  //    return new HebrewOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags);
 
-            case thaiScriptCode:
-                result = new ThaiLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
-                break;
+                case thaiScriptCode:
+                  result = new ThaiLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
+                  break;
 
-            case hangScriptCode:
-                result = new HangulOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
-                break;
+                case hangScriptCode:
+                  result = new HangulOpenTypeLayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
+                  break;
 
                     default:
                         result = new LayoutEngine(fontInstance, scriptCode, languageCode, typoFlags, success);
@@ -711,9 +722,9 @@
     }
 
     if (result && LE_FAILURE(success)) {
-                delete result;
-                result = NULL;
-        }
+      delete result;
+      result = NULL;
+    }
 
     if (result == NULL) {
         success = LE_MEMORY_ALLOCATION_ERROR;
--- a/jdk/src/share/native/sun/font/layout/LayoutEngine.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LayoutEngine.h	Fri Jan 10 15:04:46 2014 +0000
@@ -156,8 +156,8 @@
      * @param fontInstance - the font for the text
      * @param scriptCode - the script for the text
      * @param languageCode - the language for the text
-     * @param typoFlags - the typographic control flags for the text.  Set bit 1 if kerning
-     * is desired, set bit 2 if ligature formation is desired.  Others are reserved.
+     * @param typoFlags - the typographic control flags for the text (a bitfield).  Use kTypoFlagKern
+     * if kerning is desired, kTypoFlagLiga if ligature formation is desired.  Others are reserved.
      * @param success - set to an error code if the operation fails
      *
      * @see LEFontInstance
--- a/jdk/src/share/native/sun/font/layout/LigatureSubstProc2.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LigatureSubstProc2.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -105,7 +105,7 @@
         LEReferenceToArrayOf<le_uint16> componentTable(stHeader, success, componentOffset, LE_UNBOUNDED_ARRAY);
         if(LE_FAILURE(success)) {
           currGlyph+= dir;
-            return nextStateIndex; // get out! bad font
+          return nextStateIndex; // get out! bad font
         }
 
         do {
--- a/jdk/src/share/native/sun/font/layout/LigatureSubstSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LigatureSubstSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -49,14 +49,20 @@
       return 0;
     }
 
-    if (coverageIndex >= 0) {
+    LEReferenceToArrayOf<Offset> ligSetTableOffsetArrayRef(base, success, ligSetTableOffsetArray, SWAPW(ligSetCount));
+
+    if (coverageIndex >= 0 && LE_SUCCESS(success) && (le_uint32)coverageIndex < ligSetTableOffsetArrayRef.getCount()) {
         Offset ligSetTableOffset = SWAPW(ligSetTableOffsetArray[coverageIndex]);
-        const LigatureSetTable *ligSetTable = (const LigatureSetTable *) ((char *) this + ligSetTableOffset);
+        LEReferenceTo<LigatureSetTable>   ligSetTable(base, success, ligSetTableOffset);
+
+        if( LE_FAILURE(success) ) { return 0; }
         le_uint16 ligCount = SWAPW(ligSetTable->ligatureCount);
 
-        for (le_uint16 lig = 0; lig < ligCount; lig += 1) {
+        LEReferenceTo<Offset> ligatureTableOffsetArray(base, success, ligSetTable->ligatureTableOffsetArray, ligCount);
+        for (le_uint16 lig = 0; LE_SUCCESS(success) && lig < ligCount; lig += 1) {
             Offset ligTableOffset = SWAPW(ligSetTable->ligatureTableOffsetArray[lig]);
-            const LigatureTable *ligTable = (const LigatureTable *) ((char *)ligSetTable + ligTableOffset);
+            LEReferenceTo<LigatureTable>   ligTable(ligSetTable, success, ligTableOffset);
+            if(LE_FAILURE(success)) { return 0; }
             le_uint16 compCount = SWAPW(ligTable->compCount) - 1;
             le_int32 startPosition = glyphIterator->getCurrStreamPosition();
             TTGlyphID ligGlyph = SWAPW(ligTable->ligGlyph);
@@ -72,7 +78,7 @@
                 }
             }
 
-            if (comp == compCount && (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, ligGlyph)))) {
+            if (comp == compCount && (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, ligGlyph), success))) {
                 GlyphIterator tempIterator(*glyphIterator);
                 TTGlyphID deletedGlyph = tempIterator.ignoresMarks()? 0xFFFE : 0xFFFF;
 
--- a/jdk/src/share/native/sun/font/layout/LookupProcessor.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/LookupProcessor.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -60,9 +60,11 @@
       LEReferenceTo<LookupSubtable> lookupSubtable = lookupTable->getLookupSubtable(lookupTable, subtable, success);
 
         delta = applySubtable(lookupSubtable, lookupType, glyphIterator, fontInstance, success);
-
-        if (delta > 0 || LE_FAILURE(success)) {
-            return 1;
+        if (delta > 0 && LE_FAILURE(success)) {
+#if LE_TRACE
+          _LETRACE("Posn #%d, type %X, applied subtable #%d/%d - %s\n", startPosition, lookupType, subtable, subtableCount, u_errorName((UErrorCode)success));
+#endif
+          return 1;
         }
 
         glyphIterator->setCurrStreamPosition(startPosition);
@@ -86,7 +88,7 @@
     }
 
     GlyphIterator glyphIterator(glyphStorage, glyphPositionAdjustments,
-                                rightToLeft, 0, 0, glyphDefinitionTableHeader);
+                                rightToLeft, 0, 0, glyphDefinitionTableHeader, success);
     le_int32 newGlyphCount = glyphCount;
 
     for (le_uint16 order = 0; order < lookupOrderCount && LE_SUCCESS(success); order += 1) {
@@ -94,6 +96,7 @@
         FeatureMask selectMask = lookupSelectArray[lookup];
 
         if (selectMask != 0) {
+          _LETRACE("Processing order#%d/%d", order, lookupOrderCount);
           const LEReferenceTo<LookupTable> lookupTable = lookupListTable->getLookupTable(lookupListTable, lookup, success);
           if (!lookupTable.isValid() ||LE_FAILURE(success) ) {
                 continue;
@@ -103,8 +106,11 @@
             glyphIterator.reset(lookupFlags, selectMask);
 
             while (glyphIterator.findFeatureTag()) {
-              applyLookupTable(lookupTable, &glyphIterator, fontInstance, success); // TODO
+                applyLookupTable(lookupTable, &glyphIterator, fontInstance, success);
                 if (LE_FAILURE(success)) {
+#if LE_TRACE
+                    _LETRACE("Failure for lookup 0x%x - %s\n", lookup, u_errorName((UErrorCode)success));
+#endif
                     return 0;
                 }
             }
@@ -138,7 +144,7 @@
 le_int32 LookupProcessor::selectLookups(const LEReferenceTo<FeatureTable> &featureTable, FeatureMask featureMask, le_int32 order, LEErrorCode &success)
 {
   le_uint16 lookupCount = featureTable.isValid()? SWAPW(featureTable->lookupCount) : 0;
-    le_int32  store = order;
+    le_uint32  store = (le_uint32)order;
 
     LEReferenceToArrayOf<le_uint16> lookupListIndexArray(featureTable, success, featureTable->lookupListIndexArray, lookupCount);
 
@@ -147,6 +153,9 @@
       if (lookupListIndex >= lookupSelectCount) {
         continue;
       }
+      if (store >= lookupOrderCount) {
+        continue;
+      }
 
       lookupSelectArray[lookupListIndex] |= featureMask;
       lookupOrderArray[store++] = lookupListIndex;
@@ -246,7 +255,7 @@
 
     if (requiredFeatureIndex != 0xFFFF) {
       requiredFeatureTable = featureListTable->getFeatureTable(featureListTable, requiredFeatureIndex, &requiredFeatureTag, success);
-      featureReferences += SWAPW(featureTable->lookupCount);
+      featureReferences += SWAPW(requiredFeatureTable->lookupCount);
     }
 
     lookupOrderArray = LE_NEW_ARRAY(le_uint16, featureReferences);
@@ -254,6 +263,7 @@
         success = LE_MEMORY_ALLOCATION_ERROR;
         return;
     }
+    lookupOrderCount = featureReferences;
 
     for (le_int32 f = 0; f < featureMapCount; f += 1) {
         FeatureMap fm = featureMap[f];
--- a/jdk/src/share/native/sun/font/layout/Lookups.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/Lookups.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -65,7 +65,7 @@
 
   if(LE_FAILURE(success)) return 0;
 
-  return coverageTable->getGlyphCoverage(glyphID);
+  return coverageTable->getGlyphCoverage(coverageTable, glyphID, success);
 }
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/MarkArrays.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/MarkArrays.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -38,20 +38,28 @@
 
 U_NAMESPACE_BEGIN
 
-le_int32 MarkArray::getMarkClass(LEGlyphID glyphID, le_int32 coverageIndex, const LEFontInstance *fontInstance,
-                              LEPoint &anchor) const
+le_int32 MarkArray::getMarkClass(const LETableReference &base, LEGlyphID glyphID,
+                                 le_int32 coverageIndex, const LEFontInstance *fontInstance,
+                              LEPoint &anchor, LEErrorCode &success) const
 {
     le_int32 markClass = -1;
 
-    if (coverageIndex >= 0) {
+    if ( coverageIndex >= 0 && LE_SUCCESS(success) ) {
         le_uint16 mCount = SWAPW(markCount);
-
         if (coverageIndex < mCount) {
+          LEReferenceToArrayOf<MarkRecord> markRecordArrayRef(base, success, markRecordArray, mCount);
+            if(LE_FAILURE(success)) {
+              return markClass;
+            }
             const MarkRecord *markRecord = &markRecordArray[coverageIndex];
             Offset anchorTableOffset = SWAPW(markRecord->markAnchorTableOffset);
-            const AnchorTable *anchorTable = (AnchorTable *) ((char *) this + anchorTableOffset);
+            LEReferenceTo<AnchorTable> anchorTable(base, success, anchorTableOffset);
 
-            anchorTable->getAnchor(glyphID, fontInstance, anchor);
+            if(LE_FAILURE(success)) {
+              return markClass;
+            }
+
+            anchorTable->getAnchor(anchorTable, glyphID, fontInstance, anchor, success);
             markClass = SWAPW(markRecord->markClass);
         }
 
--- a/jdk/src/share/native/sun/font/layout/MarkArrays.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/MarkArrays.h	Fri Jan 10 15:04:46 2014 +0000
@@ -54,8 +54,9 @@
     le_uint16   markCount;
     MarkRecord  markRecordArray[ANY_NUMBER];
 
-    le_int32 getMarkClass(LEGlyphID glyphID, le_int32 coverageIndex, const LEFontInstance *fontInstance,
-        LEPoint &anchor) const;
+    le_int32 getMarkClass(const LETableReference &base, LEGlyphID glyphID,
+                       le_int32 coverageIndex, const LEFontInstance *fontInstance,
+                       LEPoint &anchor, LEErrorCode &success) const;
 };
 LE_VAR_ARRAY(MarkArray, markRecordArray)
 
--- a/jdk/src/share/native/sun/font/layout/MarkToBasePosnSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/MarkToBasePosnSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -66,11 +66,11 @@
     }
 
     LEPoint markAnchor;
-    const MarkArray *markArray = (const MarkArray *) ((char *) this + SWAPW(markArrayOffset));
-    le_int32 markClass = markArray->getMarkClass(markGlyph, markCoverage, fontInstance, markAnchor);
+    LEReferenceTo<MarkArray> markArray(base, success,  (const MarkArray *) ((char *) this + SWAPW(markArrayOffset)));
+    le_int32 markClass = markArray->getMarkClass(markArray, markGlyph, markCoverage, fontInstance, markAnchor, success);
     le_uint16 mcCount = SWAPW(classCount);
 
-    if (markClass < 0 || markClass >= mcCount) {
+    if (markClass < 0 || markClass >= mcCount || LE_FAILURE(success)) {
         // markGlyph isn't in the mark array or its
         // mark class is too big. The table is mal-formed!
         return 0;
@@ -80,7 +80,8 @@
     GlyphIterator baseIterator(*glyphIterator, (le_uint16) (lfIgnoreMarks /*| lfIgnoreLigatures*/));
     LEGlyphID baseGlyph = findBaseGlyph(&baseIterator);
     le_int32 baseCoverage = getBaseCoverage(base, (LEGlyphID) baseGlyph, success);
-    const BaseArray *baseArray = (const BaseArray *) ((char *) this + SWAPW(baseArrayOffset));
+    LEReferenceTo<BaseArray> baseArray(base, success, (const BaseArray *) ((char *) this + SWAPW(baseArrayOffset)));
+    if(LE_FAILURE(success)) return 0;
     le_uint16 baseCount = SWAPW(baseArray->baseRecordCount);
 
     if (baseCoverage < 0 || baseCoverage >= baseCount) {
@@ -89,19 +90,23 @@
         // table is mal-formed...
         return 0;
     }
+    LEReferenceTo<BaseRecord> baseRecord(base, success, &baseArray->baseRecordArray[baseCoverage * mcCount]);
+    if( LE_FAILURE(success) ) { return 0; }
+    LEReferenceToArrayOf<Offset> baseAnchorTableOffsetArray(base, success, &(baseRecord->baseAnchorTableOffsetArray[0]), markClass+1);
 
-    const BaseRecord *baseRecord = &baseArray->baseRecordArray[baseCoverage * mcCount];
+    if( LE_FAILURE(success) ) { return 0; }
     Offset anchorTableOffset = SWAPW(baseRecord->baseAnchorTableOffsetArray[markClass]);
-    const AnchorTable *anchorTable = (const AnchorTable *) ((char *) baseArray + anchorTableOffset);
-    LEPoint baseAnchor, markAdvance, pixels;
-
-    if (anchorTableOffset == 0) {
+    if (anchorTableOffset <= 0) {
         // this means the table is mal-formed...
         glyphIterator->setCurrGlyphBaseOffset(baseIterator.getCurrStreamPosition());
         return 0;
     }
 
-    anchorTable->getAnchor(baseGlyph, fontInstance, baseAnchor);
+    LEReferenceTo<AnchorTable> anchorTable(baseArray, success, anchorTableOffset);
+    LEPoint baseAnchor, markAdvance, pixels;
+
+
+    anchorTable->getAnchor(anchorTable, baseGlyph, fontInstance, baseAnchor, success);
 
     fontInstance->getGlyphAdvance(markGlyph, pixels);
     fontInstance->pixelsToUnits(pixels, markAdvance);
@@ -109,6 +114,8 @@
     float anchorDiffX = baseAnchor.fX - markAnchor.fX;
     float anchorDiffY = baseAnchor.fY - markAnchor.fY;
 
+    _LETRACE("Offset: (%.2f, %.2f) glyph 0x%X", anchorDiffX, anchorDiffY, markGlyph);
+
     glyphIterator->setCurrGlyphBaseOffset(baseIterator.getCurrStreamPosition());
 
     if (glyphIterator->isRightToLeft()) {
@@ -132,7 +139,6 @@
             gi.next();
         }
         // end of JK patch
-
         fontInstance->pixelsToUnits(pixels, baseAdvance);
 
         glyphIterator->setCurrGlyphPositionAdjustment(anchorDiffX - baseAdvance.fX, anchorDiffY - baseAdvance.fY, -markAdvance.fX, -markAdvance.fY);
--- a/jdk/src/share/native/sun/font/layout/MarkToLigaturePosnSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/MarkToLigaturePosnSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -65,8 +65,11 @@
     }
 
     LEPoint markAnchor;
-    const MarkArray *markArray = (const MarkArray *) ((char *) this + SWAPW(markArrayOffset));
-    le_int32 markClass = markArray->getMarkClass(markGlyph, markCoverage, fontInstance, markAnchor);
+    LEReferenceTo<MarkArray> markArray(base, success,  SWAPW(markArrayOffset));
+    if( LE_FAILURE(success) ) {
+      return 0;
+    }
+    le_int32 markClass = markArray->getMarkClass(markArray, markGlyph, markCoverage, fontInstance, markAnchor, success);
     le_uint16 mcCount = SWAPW(classCount);
 
     if (markClass < 0 || markClass >= mcCount) {
@@ -79,7 +82,7 @@
     GlyphIterator ligatureIterator(*glyphIterator, (le_uint16) (lfIgnoreMarks /*| lfIgnoreBaseGlyphs*/));
     LEGlyphID ligatureGlyph = findLigatureGlyph(&ligatureIterator);
     le_int32 ligatureCoverage = getBaseCoverage(base, (LEGlyphID) ligatureGlyph, success);
-    const LigatureArray *ligatureArray = (const LigatureArray *) ((char *) this + SWAPW(baseArrayOffset));
+    LEReferenceTo<LigatureArray> ligatureArray(base, success, SWAPW(baseArrayOffset));
     le_uint16 ligatureCount = SWAPW(ligatureArray->ligatureCount);
 
     if (ligatureCoverage < 0 || ligatureCoverage >= ligatureCount) {
@@ -91,7 +94,7 @@
 
     le_int32 markPosition = glyphIterator->getCurrStreamPosition();
     Offset ligatureAttachOffset = SWAPW(ligatureArray->ligatureAttachTableOffsetArray[ligatureCoverage]);
-    const LigatureAttachTable *ligatureAttachTable = (const LigatureAttachTable *) ((char *) ligatureArray + ligatureAttachOffset);
+    LEReferenceTo<LigatureAttachTable> ligatureAttachTable(ligatureArray, success, ligatureAttachOffset);
     le_int32 componentCount = SWAPW(ligatureAttachTable->componentCount);
     le_int32 component = ligatureIterator.getMarkComponent(markPosition);
 
@@ -100,12 +103,14 @@
         component = componentCount - 1;
     }
 
-    const ComponentRecord *componentRecord = &ligatureAttachTable->componentRecordArray[component * mcCount];
+    LEReferenceTo<ComponentRecord> componentRecord(base, success, &ligatureAttachTable->componentRecordArray[component * mcCount]);
+    LEReferenceToArrayOf<Offset> ligatureAnchorTableOffsetArray(base, success, &(componentRecord->ligatureAnchorTableOffsetArray[0]), markClass+1);
+    if( LE_FAILURE(success) ) { return 0; }
     Offset anchorTableOffset = SWAPW(componentRecord->ligatureAnchorTableOffsetArray[markClass]);
-    const AnchorTable *anchorTable = (const AnchorTable *) ((char *) ligatureAttachTable + anchorTableOffset);
+    LEReferenceTo<AnchorTable> anchorTable(ligatureAttachTable, success, anchorTableOffset);
     LEPoint ligatureAnchor, markAdvance, pixels;
 
-    anchorTable->getAnchor(ligatureGlyph, fontInstance, ligatureAnchor);
+    anchorTable->getAnchor(anchorTable, ligatureGlyph, fontInstance, ligatureAnchor, success);
 
     fontInstance->getGlyphAdvance(markGlyph, pixels);
     fontInstance->pixelsToUnits(pixels, markAdvance);
--- a/jdk/src/share/native/sun/font/layout/MarkToMarkPosnSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/MarkToMarkPosnSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -66,8 +66,11 @@
     }
 
     LEPoint markAnchor;
-    const MarkArray *markArray = (const MarkArray *) ((char *) this + SWAPW(markArrayOffset));
-    le_int32 markClass = markArray->getMarkClass(markGlyph, markCoverage, fontInstance, markAnchor);
+    LEReferenceTo<MarkArray> markArray(base, success, SWAPW(markArrayOffset));
+    if(LE_FAILURE(success)) {
+      return 0;
+    }
+    le_int32 markClass = markArray->getMarkClass(markArray, markGlyph, markCoverage, fontInstance, markAnchor, success);
     le_uint16 mcCount = SWAPW(classCount);
 
     if (markClass < 0 || markClass >= mcCount) {
@@ -79,7 +82,8 @@
     GlyphIterator mark2Iterator(*glyphIterator);
     LEGlyphID mark2Glyph = findMark2Glyph(&mark2Iterator);
     le_int32 mark2Coverage = getBaseCoverage(base, (LEGlyphID) mark2Glyph, success);
-    const Mark2Array *mark2Array = (const Mark2Array *) ((char *) this + SWAPW(baseArrayOffset));
+    LEReferenceTo<Mark2Array>  mark2Array(base, success, (const Mark2Array *) ((char *) this + SWAPW(baseArrayOffset)));
+    if(LE_FAILURE(success)) return 0;
     le_uint16 mark2Count = SWAPW(mark2Array->mark2RecordCount);
 
     if (mark2Coverage < 0 || mark2Coverage >= mark2Count) {
@@ -89,9 +93,11 @@
         return 0;
     }
 
-    const Mark2Record *mark2Record = &mark2Array->mark2RecordArray[mark2Coverage * mcCount];
+    LEReferenceTo<Mark2Record> mark2Record(base, success, &mark2Array->mark2RecordArray[mark2Coverage * mcCount]);
+    if(LE_FAILURE(success)) return 0;
     Offset anchorTableOffset = SWAPW(mark2Record->mark2AnchorTableOffsetArray[markClass]);
-    const AnchorTable *anchorTable = (const AnchorTable *) ((char *) mark2Array + anchorTableOffset);
+    LEReferenceTo<AnchorTable> anchorTable(mark2Array, success, anchorTableOffset);
+    if(LE_FAILURE(success)) return 0;
     LEPoint mark2Anchor, markAdvance, pixels;
 
     if (anchorTableOffset == 0) {
@@ -99,7 +105,7 @@
         return 0;
     }
 
-    anchorTable->getAnchor(mark2Glyph, fontInstance, mark2Anchor);
+    anchorTable->getAnchor(anchorTable, mark2Glyph, fontInstance, mark2Anchor, success);
 
     fontInstance->getGlyphAdvance(markGlyph, pixels);
     fontInstance->pixelsToUnits(pixels, markAdvance);
@@ -107,6 +113,8 @@
     float anchorDiffX = mark2Anchor.fX - markAnchor.fX;
     float anchorDiffY = mark2Anchor.fY - markAnchor.fY;
 
+    _LETRACE("Offset: (%.2f, %.2f) glyph 0x%X mark2 0x%X", anchorDiffX, anchorDiffY, markGlyph, mark2Glyph);
+
     glyphIterator->setCurrGlyphBaseOffset(mark2Iterator.getCurrStreamPosition());
 
     if (glyphIterator->isRightToLeft()) {
--- a/jdk/src/share/native/sun/font/layout/MultipleSubstSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/MultipleSubstSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -54,9 +54,10 @@
     // FIXME: is this always the right thing to do?
     // FIXME: should this only be done for a non-zero
     //        glyphCount?
-    if (filter != NULL && filter->accept(glyph)) {
+    if (filter != NULL && filter->accept(glyph, success)) {
         return 0;
     }
+    if(LE_FAILURE(success)) return 0;
 
     le_int32 coverageIndex = getGlyphCoverage(base, glyph, success);
     le_uint16 seqCount = SWAPW(sequenceCount);
@@ -67,7 +68,7 @@
 
     if (coverageIndex >= 0 && coverageIndex < seqCount) {
         Offset sequenceTableOffset = SWAPW(sequenceTableOffsetArray[coverageIndex]);
-        const SequenceTable *sequenceTable = (const SequenceTable *) ((char *) this + sequenceTableOffset);
+        LEReferenceTo<SequenceTable>   sequenceTable(base, success, sequenceTableOffset);
         le_uint16 glyphCount = SWAPW(sequenceTable->glyphCount);
 
         if (glyphCount == 0) {
@@ -76,7 +77,7 @@
         } else if (glyphCount == 1) {
             TTGlyphID substitute = SWAPW(sequenceTable->substituteArray[0]);
 
-            if (filter != NULL && ! filter->accept(LE_SET_GLYPH(glyph, substitute))) {
+            if (filter != NULL && ! filter->accept(LE_SET_GLYPH(glyph, substitute), success)) {
                 return 0;
             }
 
@@ -89,7 +90,7 @@
                 for (le_int32 i = 0; i < glyphCount; i += 1) {
                     TTGlyphID substitute = SWAPW(sequenceTable->substituteArray[i]);
 
-                    if (! filter->accept(substitute)) {
+                    if (! filter->accept(substitute, success)) {
                         return 0;
                     }
                 }
--- a/jdk/src/share/native/sun/font/layout/OpenTypeLayoutEngine.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/OpenTypeLayoutEngine.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -470,6 +470,7 @@
 void OpenTypeLayoutEngine::adjustGlyphPositions(const LEUnicode chars[], le_int32 offset, le_int32 count, le_bool reverse,
                                                 LEGlyphStorage &glyphStorage, LEErrorCode &success)
 {
+    _LETRACE("OTLE::adjustGPOS");
     if (LE_FAILURE(success)) {
         return;
     }
@@ -510,14 +511,17 @@
         if (!fGPOSTable.isEmpty()) {
             if (fScriptTagV2 != nullScriptTag &&
                 fGPOSTable->coversScriptAndLanguage(fGPOSTable, fScriptTagV2,fLangSysTag,success)) {
+              _LETRACE("OTLE::process [0]");
               fGPOSTable->process(fGPOSTable, glyphStorage, adjustments, reverse, fScriptTagV2, fLangSysTag,
                                   fGDEFTable, success, fFontInstance, fFeatureMap, fFeatureMapCount, fFeatureOrder);
 
             } else {
+              _LETRACE("OTLE::process [1]");
               fGPOSTable->process(fGPOSTable, glyphStorage, adjustments, reverse, fScriptTag, fLangSysTag,
                                   fGDEFTable, success, fFontInstance, fFeatureMap, fFeatureMapCount, fFeatureOrder);
             }
         } else if (fTypoFlags & LE_Kerning_FEATURE_FLAG) { /* kerning enabled */
+          _LETRACE("OTLE::kerning");
           LETableReference kernTable(fFontInstance, LE_KERN_TABLE_TAG, success);
           KernTable kt(kernTable, success);
           kt.process(glyphStorage, success);
@@ -546,6 +550,7 @@
 
             xPlacement = fFontInstance->xUnitsToPoints(xPlacement);
             yPlacement = fFontInstance->yUnitsToPoints(yPlacement);
+            _LETRACE("OTLE GPOS: #%d, (%.2f,%.2f)", i, xPlacement, yPlacement);
             glyphStorage.adjustPosition(i, xAdjust + xPlacement, -(yAdjust + yPlacement), success);
 
             xAdjust += fFontInstance->xUnitsToPoints(xAdvance);
--- a/jdk/src/share/native/sun/font/layout/OpenTypeUtilities.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/OpenTypeUtilities.h	Fri Jan 10 15:04:46 2014 +0000
@@ -46,15 +46,14 @@
 public:
     static le_int8 highBit(le_int32 value);
     static Offset getTagOffset(LETag tag, const LEReferenceToArrayOf<TagAndOffsetRecord> &records, LEErrorCode &success);
-    /**
-     * @deprecated TODO remove
-     */
+#if LE_ENABLE_RAW
     static le_int32 getGlyphRangeIndex(TTGlyphID glyphID, const GlyphRangeRecord *records, le_int32 recordCount) {
       LEErrorCode success = LE_NO_ERROR;
       LETableReference recordRef0((const le_uint8*)records);
       LEReferenceToArrayOf<GlyphRangeRecord> recordRef(recordRef0, success, (size_t)0, recordCount);
       return getGlyphRangeIndex(glyphID, recordRef, success);
     }
+#endif
     static le_int32 getGlyphRangeIndex(TTGlyphID glyphID, const LEReferenceToArrayOf<GlyphRangeRecord> &records, LEErrorCode &success);
     static le_int32 search(le_uint16 value, const le_uint16 array[], le_int32 count);
     static le_int32 search(le_uint32 value, const le_uint32 array[], le_int32 count);
--- a/jdk/src/share/native/sun/font/layout/PairPositioningSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/PairPositioningSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -76,19 +76,17 @@
 {
     LEGlyphID firstGlyph = glyphIterator->getCurrGlyphID();
     le_int32 coverageIndex = getGlyphCoverage(base, firstGlyph, success);
-
-    if (LE_FAILURE(success)) {
-      return 0;
-    }
     GlyphIterator tempIterator(*glyphIterator);
 
-    if (coverageIndex >= 0 && glyphIterator->next()) {
+    LEReferenceToArrayOf<Offset> pairSetTableOffsetArrayRef(base, success, pairSetTableOffsetArray, SWAPW(pairSetCount));
+
+    if (LE_SUCCESS(success) && coverageIndex >= 0 && glyphIterator->next() && (le_uint32)coverageIndex < pairSetTableOffsetArrayRef.getCount()) {
         Offset pairSetTableOffset = SWAPW(pairSetTableOffsetArray[coverageIndex]);
-        LEReferenceTo<PairSetTable> pairSetTable(base, success, ((char *) this + pairSetTableOffset));
-        if (LE_FAILURE(success)) {
-          return 0;
-        }
+        LEReferenceTo<PairSetTable> pairSetTable(base, success, pairSetTableOffset);
+        if( LE_FAILURE(success) ) return 0;
         le_uint16 pairValueCount = SWAPW(pairSetTable->pairValueCount);
+        LEReferenceTo<PairValueRecord> pairValueRecordArray(pairSetTable, success, pairSetTable->pairValueRecordArray);
+        if( LE_FAILURE(success) ) return 0;
         le_int16 valueRecord1Size = ValueRecord::getSize(SWAPW(valueFormat1));
         le_int16 valueRecord2Size = ValueRecord::getSize(SWAPW(valueFormat2));
         le_int16 recordSize = sizeof(PairValueRecord) - sizeof(ValueRecord) + valueRecord1Size + valueRecord2Size;
@@ -96,21 +94,22 @@
         LEReferenceTo<PairValueRecord> pairValueRecord;
 
         if (pairValueCount != 0) {
-            pairValueRecord = findPairValueRecord(base, (TTGlyphID) LE_GET_GLYPH(secondGlyph), pairSetTable->pairValueRecordArray, pairValueCount, recordSize, success);
+          pairValueRecord = findPairValueRecord((TTGlyphID) LE_GET_GLYPH(secondGlyph), pairValueRecordArray, pairValueCount, recordSize, success);
         }
 
-        if (pairValueRecord.isEmpty()) {
+        if (pairValueRecord.isEmpty() || LE_FAILURE(success)) {
             return 0;
         }
 
         if (valueFormat1 != 0) {
-            pairValueRecord->valueRecord1.adjustPosition(SWAPW(valueFormat1), (char *) this, tempIterator, fontInstance);
+          pairValueRecord->valueRecord1.adjustPosition(SWAPW(valueFormat1), base, tempIterator, fontInstance, success);
         }
 
         if (valueFormat2 != 0) {
-            const ValueRecord *valueRecord2 = (const ValueRecord *) ((char *) &pairValueRecord->valueRecord1 + valueRecord1Size);
-
-            valueRecord2->adjustPosition(SWAPW(valueFormat2), (char *) this, *glyphIterator, fontInstance);
+          LEReferenceTo<ValueRecord> valueRecord2(base, success, ((char *) &pairValueRecord->valueRecord1 + valueRecord1Size));
+          if(LE_SUCCESS(success)) {
+            valueRecord2->adjustPosition(SWAPW(valueFormat2), base, *glyphIterator, fontInstance, success);
+          }
         }
 
         // back up glyphIterator so second glyph can be
@@ -135,26 +134,28 @@
 
     if (coverageIndex >= 0 && glyphIterator->next()) {
         LEGlyphID secondGlyph = glyphIterator->getCurrGlyphID();
-        const ClassDefinitionTable *classDef1 = (const ClassDefinitionTable *) ((char *) this + SWAPW(classDef1Offset));
-        const ClassDefinitionTable *classDef2 = (const ClassDefinitionTable *) ((char *) this + SWAPW(classDef2Offset));
-        le_int32 class1 = classDef1->getGlyphClass(firstGlyph);
-        le_int32 class2 = classDef2->getGlyphClass(secondGlyph);
+        const LEReferenceTo<ClassDefinitionTable> classDef1(base, success, SWAPW(classDef1Offset));
+        const LEReferenceTo<ClassDefinitionTable> classDef2(base, success, SWAPW(classDef2Offset));
+        le_int32 class1 = classDef1->getGlyphClass(classDef1, firstGlyph, success);
+        le_int32 class2 = classDef2->getGlyphClass(classDef2, secondGlyph, success);
         le_int16 valueRecord1Size = ValueRecord::getSize(SWAPW(valueFormat1));
         le_int16 valueRecord2Size = ValueRecord::getSize(SWAPW(valueFormat2));
         le_int16 class2RecordSize = valueRecord1Size + valueRecord2Size;
         le_int16 class1RecordSize = class2RecordSize * SWAPW(class2Count);
-        const Class1Record *class1Record = (const Class1Record *) ((char *) class1RecordArray + (class1RecordSize * class1));
-        const Class2Record *class2Record = (const Class2Record *) ((char *) class1Record->class2RecordArray + (class2RecordSize * class2));
-
+        const LEReferenceTo<Class1Record> class1Record(base, success, (const Class1Record *) ((char *) class1RecordArray + (class1RecordSize * class1)));
+        const LEReferenceTo<Class2Record> class2Record(base, success, (const Class2Record *) ((char *) class1Record->class2RecordArray + (class2RecordSize * class2)));
 
-        if (valueFormat1 != 0) {
-            class2Record->valueRecord1.adjustPosition(SWAPW(valueFormat1), (char *) this, tempIterator, fontInstance);
-        }
-
-        if (valueFormat2 != 0) {
-            const ValueRecord *valueRecord2 = (const ValueRecord *) ((char *) &class2Record->valueRecord1 + valueRecord1Size);
-
-            valueRecord2->adjustPosition(SWAPW(valueFormat2), (const char *) this, *glyphIterator, fontInstance);
+        if( LE_SUCCESS(success) ) {
+          if (valueFormat1 != 0) {
+            class2Record->valueRecord1.adjustPosition(SWAPW(valueFormat1), base, tempIterator, fontInstance, success);
+          }
+          if (valueFormat2 != 0) {
+            const LEReferenceTo<ValueRecord> valueRecord2(base, success, ((char *) &class2Record->valueRecord1) + valueRecord1Size);
+            LEReferenceTo<PairPositioningFormat2Subtable> thisRef(base, success, this);
+            if(LE_SUCCESS(success)) {
+              valueRecord2->adjustPosition(SWAPW(valueFormat2), thisRef, *glyphIterator, fontInstance, success);
+            }
+          }
         }
 
         // back up glyphIterator so second glyph can be
@@ -166,23 +167,24 @@
     return 0;
 }
 
-LEReferenceTo<PairValueRecord> PairPositioningFormat1Subtable::findPairValueRecord(const LETableReference &base, TTGlyphID glyphID, const PairValueRecord *records, le_uint16 recordCount, le_uint16 recordSize, LEErrorCode &success) const
+LEReferenceTo<PairValueRecord>
+PairPositioningFormat1Subtable::findPairValueRecord(TTGlyphID glyphID, LEReferenceTo<PairValueRecord>& records,
+                                                    le_uint16 recordCount,
+                                                    le_uint16 recordSize, LEErrorCode &success) const
 {
 #if 1
         // The OpenType spec. says that the ValueRecord table is
         // sorted by secondGlyph. Unfortunately, there are fonts
         // around that have an unsorted ValueRecord table.
-        LEReferenceTo<PairValueRecord> record(base, success, records);
-        record.verifyLength(0, recordSize, success);
+        LEReferenceTo<PairValueRecord> record(records);
 
         for(le_int32 r = 0; r < recordCount; r += 1) {
-           if (LE_FAILURE(success)) return (const PairValueRecord*)NULL;
-                if (SWAPW(record->secondGlyph) == glyphID) {
-                        return record;
-                }
+          if(LE_FAILURE(success)) return LEReferenceTo<PairValueRecord>();
+          if (SWAPW(record->secondGlyph) == glyphID) {
+            return record;
+          }
 
-                record =  LEReferenceTo<PairValueRecord>(base, success, ((const char*)record.getAlias())+ recordSize);
-                record.verifyLength(0, recordSize, success);
+          record.addOffset(recordSize, success);
         }
 #else
   #error dead code - not updated.
@@ -211,7 +213,7 @@
     }
 #endif
 
-    return (const PairValueRecord*)NULL;
+    return LEReferenceTo<PairValueRecord>();
 }
 
 U_NAMESPACE_END
--- a/jdk/src/share/native/sun/font/layout/PairPositioningSubtables.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/PairPositioningSubtables.h	Fri Jan 10 15:04:46 2014 +0000
@@ -77,9 +77,8 @@
     le_uint32  process(const LEReferenceTo<PairPositioningFormat1Subtable> &base, GlyphIterator *glyphIterator, const LEFontInstance *fontInstance, LEErrorCode &success) const;
 
 private:
-    LEReferenceTo<PairValueRecord> findPairValueRecord(const LETableReference &base, TTGlyphID glyphID, const PairValueRecord *records,
+    LEReferenceTo<PairValueRecord> findPairValueRecord(TTGlyphID glyphID, LEReferenceTo<PairValueRecord> &records,
         le_uint16 recordCount, le_uint16 recordSize, LEErrorCode &success) const;
-
 };
 LE_VAR_ARRAY(PairPositioningFormat1Subtable, pairSetTableOffsetArray)
 
--- a/jdk/src/share/native/sun/font/layout/ScriptAndLanguage.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ScriptAndLanguage.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -106,7 +106,8 @@
         }
     } else {
       LEReferenceToArrayOf<ScriptRecord> scriptRecordArrayRef(base, success, &scriptRecordArray[0], count);
-      scriptTableOffset = OpenTypeUtilities::getTagOffset(scriptTag, scriptRecordArrayRef, success); // TODO
+
+      scriptTableOffset = OpenTypeUtilities::getTagOffset(scriptTag, scriptRecordArrayRef, success);
     }
 
     if (scriptTableOffset != 0) {
--- a/jdk/src/share/native/sun/font/layout/ScriptAndLanguageTags.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ScriptAndLanguageTags.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -126,13 +126,13 @@
     linaScriptTag, /* 'lina' (LINA) */
     mandScriptTag, /* 'mand' (MANDAIC) */
     mayaScriptTag, /* 'maya' (MAYA) */
-    meroScriptTag, /* 'mero' (MERO) */
+    meroScriptTag, /* 'mero' (MEROITIC_HIEROGLYPHS) */
     nkooScriptTag, /* 'nko ' (NKO) */
     orkhScriptTag, /* 'orkh' (OLD_TURKIC) */
     permScriptTag, /* 'perm' (PERM) */
     phagScriptTag, /* 'phag' (PHAGS_PA) */
     phnxScriptTag, /* 'phnx' (PHOENICIAN) */
-    plrdScriptTag, /* 'plrd' (PLRD) */
+    plrdScriptTag, /* 'plrd' (MIAO/POLLARD) */
     roroScriptTag, /* 'roro' (RORO) */
     saraScriptTag, /* 'sara' (SARA) */
     syreScriptTag, /* 'syre' (SYRE) */
@@ -158,7 +158,7 @@
     mteiScriptTag, /* 'mtei' (MEETEI_MAYEK) */
     armiScriptTag, /* 'armi' (IMPERIAL_ARAMAIC) */
     avstScriptTag, /* 'avst' (AVESTAN) */
-    cakmScriptTag, /* 'cakm' (CAKM) */
+    cakmScriptTag, /* 'cakm' (CHAKMA) */
     koreScriptTag, /* 'kore' (KORE) */
     kthiScriptTag, /* 'kthi' (KAITHI) */
     maniScriptTag, /* 'mani' (MANI) */
@@ -181,7 +181,7 @@
     kpelScriptTag, /* 'kpel' (KPEL) */
     lomaScriptTag, /* 'loma' (LOMA) */
     mendScriptTag, /* 'mend' (MEND) */
-    mercScriptTag, /* 'merc' (MERC) */
+    mercScriptTag, /* 'merc' (MEROITIC_CURSIVE) */
     narbScriptTag, /* 'narb' (NARB) */
     nbatScriptTag, /* 'nbat' (NBAT) */
     palmScriptTag, /* 'palm' (PALM) */
--- a/jdk/src/share/native/sun/font/layout/ScriptAndLanguageTags.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ScriptAndLanguageTags.h	Fri Jan 10 15:04:46 2014 +0000
@@ -140,13 +140,13 @@
 const LETag linaScriptTag = 0x6C696E61; /* 'lina' (LINA) */
 const LETag mandScriptTag = 0x6D616E64; /* 'mand' (MANDAIC) */
 const LETag mayaScriptTag = 0x6D617961; /* 'maya' (MAYA) */
-const LETag meroScriptTag = 0x6D65726F; /* 'mero' (MERO) */
+const LETag meroScriptTag = 0x6D65726F; /* 'mero' (MEROITIC_HIEROGLYPHS) */
 const LETag nkooScriptTag = 0x6E6B6F20; /* 'nko ' (NKO) */
 const LETag orkhScriptTag = 0x6F726B68; /* 'orkh' (OLD_TURKIC) */
 const LETag permScriptTag = 0x7065726D; /* 'perm' (PERM) */
 const LETag phagScriptTag = 0x70686167; /* 'phag' (PHAGS_PA) */
 const LETag phnxScriptTag = 0x70686E78; /* 'phnx' (PHOENICIAN) */
-const LETag plrdScriptTag = 0x706C7264; /* 'plrd' (PLRD) */
+const LETag plrdScriptTag = 0x706C7264; /* 'plrd' (MIAO) */
 const LETag roroScriptTag = 0x726F726F; /* 'roro' (RORO) */
 const LETag saraScriptTag = 0x73617261; /* 'sara' (SARA) */
 const LETag syreScriptTag = 0x73797265; /* 'syre' (SYRE) */
@@ -172,7 +172,7 @@
 const LETag mteiScriptTag = 0x6D746569; /* 'mtei' (MEETEI_MAYEK) */
 const LETag armiScriptTag = 0x61726D69; /* 'armi' (IMPERIAL_ARAMAIC) */
 const LETag avstScriptTag = 0x61767374; /* 'avst' (AVESTAN) */
-const LETag cakmScriptTag = 0x63616B6D; /* 'cakm' (CAKM) */
+const LETag cakmScriptTag = 0x63616B6D; /* 'cakm' (CHAKMA) */
 const LETag koreScriptTag = 0x6B6F7265; /* 'kore' (KORE) */
 const LETag kthiScriptTag = 0x6B746869; /* 'kthi' (KAITHI) */
 const LETag maniScriptTag = 0x6D616E69; /* 'mani' (MANI) */
@@ -195,7 +195,7 @@
 const LETag kpelScriptTag = 0x6B70656C; /* 'kpel' (KPEL) */
 const LETag lomaScriptTag = 0x6C6F6D61; /* 'loma' (LOMA) */
 const LETag mendScriptTag = 0x6D656E64; /* 'mend' (MEND) */
-const LETag mercScriptTag = 0x6D657263; /* 'merc' (MERC) */
+const LETag mercScriptTag = 0x6D657263; /* 'merc' (MEROITIC_CURSIVE) */
 const LETag narbScriptTag = 0x6E617262; /* 'narb' (NARB) */
 const LETag nbatScriptTag = 0x6E626174; /* 'nbat' (NBAT) */
 const LETag palmScriptTag = 0x70616C6D; /* 'palm' (PALM) */
--- a/jdk/src/share/native/sun/font/layout/SegmentArrayProcessor2.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/SegmentArrayProcessor2.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -65,17 +65,18 @@
 
     for (glyph = 0; glyph < glyphCount; glyph += 1) {
         LEGlyphID thisGlyph = glyphStorage[glyph];
+        // lookupSegment already range checked by lookupSegment() function.
         const LookupSegment *lookupSegment = segmentArrayLookupTable->lookupSegment(segmentArrayLookupTable, segments, thisGlyph, success);
 
-        if (lookupSegment != NULL)  {
+        if (lookupSegment != NULL&& LE_SUCCESS(success))  {
             TTGlyphID firstGlyph = SWAPW(lookupSegment->firstGlyph);
+            TTGlyphID lastGlyph = SWAPW(lookupSegment->lastGlyph);
             le_int16  offset = SWAPW(lookupSegment->value);
-
-            if (offset != 0) {
-              TTGlyphID  *glyphArray = (TTGlyphID *) ((char *) subtableHeader.getAliasTODO() + offset);
-                TTGlyphID   newGlyph   = SWAPW(glyphArray[LE_GET_GLYPH(thisGlyph) - firstGlyph]);
-
-                glyphStorage[glyph] = LE_SET_GLYPH(thisGlyph, newGlyph);
+            TTGlyphID thisGlyphId=  LE_GET_GLYPH(thisGlyph);
+            LEReferenceToArrayOf<TTGlyphID> glyphArray(subtableHeader, success, offset, lastGlyph - firstGlyph + 1);
+            if (offset != 0 && thisGlyphId <= lastGlyph && thisGlyphId >= firstGlyph && LE_SUCCESS(success) ) {
+              TTGlyphID   newGlyph   = SWAPW(glyphArray[thisGlyphId]);
+              glyphStorage[glyph] = LE_SET_GLYPH(thisGlyph, newGlyph);
             }
         }
     }
--- a/jdk/src/share/native/sun/font/layout/SinglePositioningSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/SinglePositioningSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -75,7 +75,7 @@
     }
 
     if (coverageIndex >= 0) {
-        valueRecord.adjustPosition(SWAPW(valueFormat), (const char *) this, *glyphIterator, fontInstance);
+      valueRecord.adjustPosition(SWAPW(valueFormat), base, *glyphIterator, fontInstance, success);
 
         return 1;
     }
@@ -92,7 +92,7 @@
     }
 
     if (coverageIndex >= 0) {
-        valueRecordArray[0].adjustPosition(coverageIndex, SWAPW(valueFormat), (const char *) this, *glyphIterator, fontInstance);
+      valueRecordArray[0].adjustPosition(coverageIndex, SWAPW(valueFormat), base, *glyphIterator, fontInstance, success);
 
         return 1;
     }
--- a/jdk/src/share/native/sun/font/layout/SingleSubstitutionSubtables.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/SingleSubstitutionSubtables.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -76,7 +76,7 @@
     if (coverageIndex >= 0) {
         TTGlyphID substitute = ((TTGlyphID) LE_GET_GLYPH(glyph)) + SWAPW(deltaGlyphID);
 
-        if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, substitute))) {
+        if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, substitute), success)) {
             glyphIterator->setCurrGlyphID(substitute);
         }
 
@@ -97,7 +97,7 @@
     if (coverageIndex >= 0) {
         TTGlyphID substitute = SWAPW(substituteArray[coverageIndex]);
 
-        if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, substitute))) {
+        if (filter == NULL || filter->accept(LE_SET_GLYPH(glyph, substitute), success)) {
             glyphIterator->setCurrGlyphID(substitute);
         }
 
--- a/jdk/src/share/native/sun/font/layout/TibetanReordering.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/TibetanReordering.h	Fri Jan 10 15:04:46 2014 +0000
@@ -39,7 +39,7 @@
  */
 
 #ifndef __TIBETANREORDERING_H
-#define __TIBETANORDERING_H
+#define __TIBETANREORDERING_H
 
 /**
  * \file
--- a/jdk/src/share/native/sun/font/layout/ValueRecords.cpp	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ValueRecords.cpp	Fri Jan 10 15:04:46 2014 +0000
@@ -59,8 +59,8 @@
     return SWAPW(value);
 }
 
-void ValueRecord::adjustPosition(ValueFormat valueFormat, const char *base, GlyphIterator &glyphIterator,
-                                 const LEFontInstance *fontInstance) const
+void ValueRecord::adjustPosition(ValueFormat valueFormat, const LETableReference& base, GlyphIterator &glyphIterator,
+                                 const LEFontInstance *fontInstance, LEErrorCode &success) const
 {
     float xPlacementAdjustment = 0;
     float yPlacementAdjustment = 0;
@@ -118,8 +118,8 @@
             Offset dtOffset = getFieldValue(valueFormat, vrfXPlaDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 xAdj = dt->getAdjustment(xppem);
+                 LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 xAdj = dt->getAdjustment(dt, xppem, success);
 
                 xPlacementAdjustment += fontInstance->xPixelsToUnits(xAdj);
             }
@@ -129,8 +129,8 @@
             Offset dtOffset = getFieldValue(valueFormat, vrfYPlaDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 yAdj = dt->getAdjustment(yppem);
+                 LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 yAdj = dt->getAdjustment(dt, yppem, success);
 
                 yPlacementAdjustment += fontInstance->yPixelsToUnits(yAdj);
             }
@@ -140,8 +140,8 @@
             Offset dtOffset = getFieldValue(valueFormat, vrfXAdvDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 xAdj = dt->getAdjustment(xppem);
+                 LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 xAdj = dt->getAdjustment(dt, xppem, success);
 
                 xAdvanceAdjustment += fontInstance->xPixelsToUnits(xAdj);
             }
@@ -151,10 +151,10 @@
             Offset dtOffset = getFieldValue(valueFormat, vrfYAdvDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 yAdj = dt->getAdjustment(yppem);
+              LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+              le_int16 yAdj = dt->getAdjustment(dt, yppem, success);
 
-                yAdvanceAdjustment += fontInstance->yPixelsToUnits(yAdj);
+              yAdvanceAdjustment += fontInstance->yPixelsToUnits(yAdj);
             }
         }
     }
@@ -163,8 +163,8 @@
         xPlacementAdjustment, yPlacementAdjustment, xAdvanceAdjustment, yAdvanceAdjustment);
 }
 
-void ValueRecord::adjustPosition(le_int16 index, ValueFormat valueFormat, const char *base, GlyphIterator &glyphIterator,
-                                 const LEFontInstance *fontInstance) const
+void ValueRecord::adjustPosition(le_int16 index, ValueFormat valueFormat, const LETableReference& base, GlyphIterator &glyphIterator,
+                                 const LEFontInstance *fontInstance, LEErrorCode &success) const
 {
     float xPlacementAdjustment = 0;
     float yPlacementAdjustment = 0;
@@ -222,8 +222,8 @@
             Offset dtOffset = getFieldValue(index, valueFormat, vrfXPlaDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 xAdj = dt->getAdjustment(xppem);
+                LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 xAdj = dt->getAdjustment(dt, xppem, success);
 
                 xPlacementAdjustment += fontInstance->xPixelsToUnits(xAdj);
             }
@@ -233,8 +233,8 @@
             Offset dtOffset = getFieldValue(index, valueFormat, vrfYPlaDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 yAdj = dt->getAdjustment(yppem);
+                LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 yAdj = dt->getAdjustment(dt, yppem, success);
 
                 yPlacementAdjustment += fontInstance->yPixelsToUnits(yAdj);
             }
@@ -244,8 +244,8 @@
             Offset dtOffset = getFieldValue(index, valueFormat, vrfXAdvDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 xAdj = dt->getAdjustment(xppem);
+                LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 xAdj = dt->getAdjustment(dt, xppem, success);
 
                 xAdvanceAdjustment += fontInstance->xPixelsToUnits(xAdj);
             }
@@ -255,8 +255,8 @@
             Offset dtOffset = getFieldValue(index, valueFormat, vrfYAdvDevice);
 
             if (dtOffset != 0) {
-                const DeviceTable *dt = (const DeviceTable *) (base + dtOffset);
-                le_int16 yAdj = dt->getAdjustment(yppem);
+                LEReferenceTo<DeviceTable> dt(base, success, dtOffset);
+                le_int16 yAdj = dt->getAdjustment(dt, yppem, success);
 
                 yAdvanceAdjustment += fontInstance->yPixelsToUnits(yAdj);
             }
--- a/jdk/src/share/native/sun/font/layout/ValueRecords.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/font/layout/ValueRecords.h	Fri Jan 10 15:04:46 2014 +0000
@@ -53,10 +53,10 @@
 
     le_int16   getFieldValue(ValueFormat valueFormat, ValueRecordField field) const;
     le_int16   getFieldValue(le_int16 index, ValueFormat valueFormat, ValueRecordField field) const;
-    void    adjustPosition(ValueFormat valueFormat, const char *base, GlyphIterator &glyphIterator,
-                const LEFontInstance *fontInstance) const;
-    void    adjustPosition(le_int16 index, ValueFormat valueFormat, const char *base, GlyphIterator &glyphIterator,
-                const LEFontInstance *fontInstance) const;
+    void    adjustPosition(ValueFormat valueFormat, const LETableReference &base, GlyphIterator &glyphIterator,
+                const LEFontInstance *fontInstance, LEErrorCode &success) const;
+    void    adjustPosition(le_int16 index, ValueFormat valueFormat, const LETableReference &base, GlyphIterator &glyphIterator,
+                const LEFontInstance *fontInstance, LEErrorCode &success) const;
 
     static le_int16    getSize(ValueFormat valueFormat);
 
--- a/jdk/src/share/native/sun/java2d/cmm/lcms/cmsintrp.c	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/share/native/sun/java2d/cmm/lcms/cmsintrp.c	Fri Jan 10 15:04:46 2014 +0000
@@ -215,6 +215,11 @@
     Output[0] = LinearInterp(rest, y0, y1);
 }
 
+// To prevent out of bounds indexing
+cmsINLINE cmsFloat32Number fclamp(cmsFloat32Number v)
+{
+    return v < 0.0f ? 0.0f : (v > 1.0f ? 1.0f : v);
+}
 
 // Floating-point version of 1D interpolation
 static
@@ -227,13 +232,15 @@
        int cell0, cell1;
        const cmsFloat32Number* LutTable = (cmsFloat32Number*) p ->Table;
 
+       val2 = fclamp(Value[0]);
+
        // if last value...
-       if (Value[0] == 1.0) {
+       if (val2 == 1.0) {
            Output[0] = LutTable[p -> Domain[0]];
            return;
        }
 
-       val2 = p -> Domain[0] * Value[0];
+       val2 *= p -> Domain[0];
 
        cell0 = (int) floor(val2);
        cell1 = (int) ceil(val2);
@@ -292,13 +299,15 @@
     cmsUInt32Number OutChan;
     const cmsFloat32Number* LutTable = (cmsFloat32Number*) p ->Table;
 
+    val2 = fclamp(Value[0]);
+
         // if last value...
-       if (Value[0] == 1.0) {
+       if (val2 == 1.0) {
            Output[0] = LutTable[p -> Domain[0]];
            return;
        }
 
-       val2 = p -> Domain[0] * Value[0];
+       val2 *= p -> Domain[0];
 
        cell0 = (int) floor(val2);
        cell1 = (int) ceil(val2);
@@ -339,8 +348,8 @@
         dxy;
 
     TotalOut   = p -> nOutputs;
-    px = Input[0] * p->Domain[0];
-    py = Input[1] * p->Domain[1];
+    px = fclamp(Input[0]) * p->Domain[0];
+    py = fclamp(Input[1]) * p->Domain[1];
 
     x0 = (int) _cmsQuickFloor(px); fx = px - (cmsFloat32Number) x0;
     y0 = (int) _cmsQuickFloor(py); fy = py - (cmsFloat32Number) y0;
@@ -454,20 +463,9 @@
     TotalOut   = p -> nOutputs;
 
     // We need some clipping here
-    px = Input[0];
-    py = Input[1];
-    pz = Input[2];
-
-    if (px < 0) px = 0;
-    if (px > 1) px = 1;
-    if (py < 0) py = 0;
-    if (py > 1) py = 1;
-    if (pz < 0) pz = 0;
-    if (pz > 1) pz = 1;
-
-    px *= p->Domain[0];
-    py *= p->Domain[1];
-    pz *= p->Domain[2];
+    px = fclamp(Input[0]) * p->Domain[0];
+    py = fclamp(Input[1]) * p->Domain[1];
+    pz = fclamp(Input[2]) * p->Domain[2];
 
     x0 = (int) _cmsQuickFloor(px); fx = px - (cmsFloat32Number) x0;
     y0 = (int) _cmsQuickFloor(py); fy = py - (cmsFloat32Number) y0;
@@ -609,20 +607,9 @@
     TotalOut   = p -> nOutputs;
 
     // We need some clipping here
-    px = Input[0];
-    py = Input[1];
-    pz = Input[2];
-
-    if (px < 0) px = 0;
-    if (px > 1) px = 1;
-    if (py < 0) py = 0;
-    if (py > 1) py = 1;
-    if (pz < 0) pz = 0;
-    if (pz > 1) pz = 1;
-
-    px *= p->Domain[0];
-    py *= p->Domain[1];
-    pz *= p->Domain[2];
+    px = fclamp(Input[0]) * p->Domain[0];
+    py = fclamp(Input[1]) * p->Domain[1];
+    pz = fclamp(Input[2]) * p->Domain[2];
 
     x0 = (int) _cmsQuickFloor(px); rx = (px - (cmsFloat32Number) x0);
     y0 = (int) _cmsQuickFloor(py); ry = (py - (cmsFloat32Number) y0);
@@ -1039,8 +1026,7 @@
        cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
        cmsInterpParams p1;
 
-
-       pk = Input[0] * p->Domain[0];
+       pk = fclamp(Input[0]) * p->Domain[0];
        k0 = _cmsQuickFloor(pk);
        rest = pk - (cmsFloat32Number) k0;
 
@@ -1127,7 +1113,7 @@
        cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
        cmsInterpParams p1;
 
-       pk = Input[0] * p->Domain[0];
+       pk = fclamp(Input[0]) * p->Domain[0];
        k0 = _cmsQuickFloor(pk);
        rest = pk - (cmsFloat32Number) k0;
 
@@ -1214,7 +1200,7 @@
        cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
        cmsInterpParams p1;
 
-       pk = Input[0] * p->Domain[0];
+       pk = fclamp(Input[0]) * p->Domain[0];
        k0 = _cmsQuickFloor(pk);
        rest = pk - (cmsFloat32Number) k0;
 
@@ -1299,7 +1285,7 @@
        cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
        cmsInterpParams p1;
 
-       pk = Input[0] * p->Domain[0];
+       pk = fclamp(Input[0]) * p->Domain[0];
        k0 = _cmsQuickFloor(pk);
        rest = pk - (cmsFloat32Number) k0;
 
@@ -1384,7 +1370,7 @@
        cmsFloat32Number Tmp1[MAX_STAGE_CHANNELS], Tmp2[MAX_STAGE_CHANNELS];
        cmsInterpParams p1;
 
-       pk = Input[0] * p->Domain[0];
+       pk = fclamp(Input[0]) * p->Domain[0];
        k0 = _cmsQuickFloor(pk);
        rest = pk - (cmsFloat32Number) k0;
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/solaris/classes/sun/net/PortConfig.java	Fri Jan 10 15:04:46 2014 +0000
@@ -0,0 +1,89 @@
+/*
+ * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.net;
+
+import java.security.AccessController;
+
+/**
+ * Determines the ephemeral port range in use on this system.
+ * If this cannot be determined, then the default settings
+ * of the OS are returned.
+ */
+
+public final class PortConfig {
+
+    private static int defaultUpper, defaultLower;
+    private final static int upper, lower;
+
+    private PortConfig() {}
+
+    static {
+        AccessController.doPrivileged(
+            new java.security.PrivilegedAction<Void>() {
+                public Void run() {
+                    System.loadLibrary("net");
+                    String os = System.getProperty("os.name");
+                    if (os.startsWith("Linux")) {
+                        defaultLower = 32768;
+                        defaultUpper = 61000;
+                    } else if (os.startsWith("SunOS")) {
+                        defaultLower = 32768;
+                        defaultUpper = 65535;
+                    } else if (os.contains("OS X")) {
+                        defaultLower = 49152;
+                        defaultUpper = 65535;
+                    } else {
+                        throw new InternalError(
+                            "sun.net.PortConfig: unknown OS");
+                    }
+                    return null;
+                }
+            });
+
+        int v = getLower0();
+        if (v == -1) {
+            v = defaultLower;
+        }
+        lower = v;
+
+        v = getUpper0();
+        if (v == -1) {
+            v = defaultUpper;
+        }
+        upper = v;
+    }
+
+    static native int getLower0();
+    static native int getUpper0();
+
+    public static int getLower() {
+        return lower;
+    }
+
+    public static int getUpper() {
+        return upper;
+    }
+}
--- a/jdk/src/solaris/classes/sun/nio/ch/sctp/SctpChannelImpl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/solaris/classes/sun/nio/ch/sctp/SctpChannelImpl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -187,6 +187,10 @@
                         SctpNet.throwAlreadyBoundException();
                     InetSocketAddress isa = (local == null) ?
                         new InetSocketAddress(0) : Net.checkAddress(local);
+                    SecurityManager sm = System.getSecurityManager();
+                    if (sm != null) {
+                        sm.checkListen(isa.getPort());
+                    }
                     Net.bind(fd, isa.getAddress(), isa.getPort());
                     InetSocketAddress boundIsa = Net.localAddress(fd);
                     port = boundIsa.getPort();
--- a/jdk/src/solaris/native/java/net/net_util_md.c	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/solaris/native/java/net/net_util_md.c	Fri Jan 10 15:04:46 2014 +0000
@@ -138,8 +138,7 @@
  * of the parameter is assumed to be an 'int'. If the parameter
  * cannot be obtained return -1
  */
-static int
-getParam(char *driver, char *param)
+int net_getParam(char *driver, char *param)
 {
     struct strioctl stri;
     char buf [64];
@@ -166,7 +165,7 @@
 
 /*
  * Iterative way to find the max value that SO_SNDBUF or SO_RCVBUF
- * for Solaris versions that do not support the ioctl() in getParam().
+ * for Solaris versions that do not support the ioctl() in net_getParam().
  * Ugly, but only called once (for each sotype).
  *
  * As an optimization, we make a guess using the default values for Solaris
@@ -1359,7 +1358,7 @@
              * If that fails, we use the search algorithm in findMaxBuf()
              */
             if (!init_tcp_max_buf && sotype == SOCK_STREAM) {
-                tcp_max_buf = getParam("/dev/tcp", "tcp_max_buf");
+                tcp_max_buf = net_getParam("/dev/tcp", "tcp_max_buf");
                 if (tcp_max_buf == -1) {
                     tcp_max_buf = findMaxBuf(fd, opt, SOCK_STREAM);
                     if (tcp_max_buf == -1) {
@@ -1368,7 +1367,7 @@
                 }
                 init_tcp_max_buf = 1;
             } else if (!init_udp_max_buf && sotype == SOCK_DGRAM) {
-                udp_max_buf = getParam("/dev/udp", "udp_max_buf");
+                udp_max_buf = net_getParam("/dev/udp", "udp_max_buf");
                 if (udp_max_buf == -1) {
                     udp_max_buf = findMaxBuf(fd, opt, SOCK_DGRAM);
                     if (udp_max_buf == -1) {
--- a/jdk/src/solaris/native/java/net/net_util_md.h	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/solaris/native/java/net/net_util_md.h	Fri Jan 10 15:04:46 2014 +0000
@@ -81,6 +81,9 @@
 int getDefaultIPv6Interface(struct in6_addr *target_addr);
 #endif
 
+#ifdef __solaris__
+extern int net_getParam(char *driver, char *param);
+#endif
 
 /* needed from libsocket on Solaris 8 */
 
--- a/jdk/src/solaris/native/sun/awt/splashscreen/splashscreen_sys.c	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/solaris/native/sun/awt/splashscreen/splashscreen_sys.c	Fri Jan 10 15:04:46 2014 +0000
@@ -577,8 +577,8 @@
         SplashUnlock(splash);
         rc = poll(pfd, 2, timeout);
         SplashLock(splash);
-        if (splash->isVisible>0 && SplashTime() >= splash->time +
-                splash->frames[splash->currentFrame].delay) {
+        if (splash->isVisible > 0 && splash->currentFrame >= 0 &&
+                SplashTime() >= splash->time + splash->frames[splash->currentFrame].delay) {
             SplashNextFrame(splash);
             SplashUpdateShape(splash);
             SplashRedrawWindow(splash);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/solaris/native/sun/net/portconfig.c	Fri Jan 10 15:04:46 2014 +0000
@@ -0,0 +1,123 @@
+/*
+ * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <errno.h>
+
+#if defined(_ALLBSD_SOURCE)
+#include <sys/sysctl.h>
+#endif
+
+#include "jni.h"
+#include "net_util.h"
+#include "sun_net_PortConfig.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct portrange {
+    int lower;
+    int higher;
+};
+
+static int getPortRange(struct portrange *range)
+{
+#ifdef __linux__
+    {
+        FILE *f;
+        int ret;
+
+        f = fopen("/proc/sys/net/ipv4/ip_local_port_range", "r");
+        if (f != NULL) {
+            ret = fscanf(f, "%d %d", &range->lower, &range->higher);
+            fclose(f);
+            return ret == 2 ? 0 : -1;
+        }
+        return -1;
+    }
+
+#elif defined(__solaris__)
+    {
+        range->higher = net_getParam("/dev/tcp", "tcp_largest_anon_port");
+        range->lower = net_getParam("/dev/tcp", "tcp_smallest_anon_port");
+        return 0;
+    }
+#elif defined(_ALLBSD_SOURCE)
+    {
+        int ret;
+        size_t size = sizeof(range->lower);
+        ret = sysctlbyname(
+            "net.inet.ip.portrange.first", &range->lower, &size, 0, 0
+        );
+        if (ret == -1) {
+            return -1;
+        }
+        size = sizeof(range->higher);
+        ret = sysctlbyname(
+            "net.inet.ip.portrange.last", &range->higher, &size, 0, 0
+        );
+        return ret;
+    }
+#else
+    return -1;
+#endif
+}
+
+/*
+ * Class:     sun_net_PortConfig
+ * Method:    getLower0
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_sun_net_PortConfig_getLower0
+  (JNIEnv *env, jclass clazz)
+{
+    struct portrange range;
+    if (getPortRange(&range) < 0) {
+        return -1;
+    }
+    return range.lower;
+}
+
+/*
+ * Class:     sun_net_PortConfig
+ * Method:    getUpper0
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_sun_net_PortConfig_getUpper0
+  (JNIEnv *env, jclass clazz)
+{
+    struct portrange range;
+    if (getPortRange(&range) < 0) {
+        return -1;
+    }
+    return range.higher;
+}
+
+#ifdef __cplusplus
+}
+#endif
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/windows/classes/sun/net/PortConfig.java	Fri Jan 10 15:04:46 2014 +0000
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.net;
+
+import java.security.AccessController;
+
+/**
+ * Determines the ephemeral port range in use on this system.
+ * If this cannot be determined, then the default settings
+ * of the OS are returned.
+ */
+
+public final class PortConfig {
+
+    private static int defaultUpper, defaultLower;
+    private final static int upper, lower;
+
+    static {
+        AccessController.doPrivileged(
+            new java.security.PrivilegedAction<Void>() {
+                public Void run() {
+                    System.loadLibrary("net");
+                    return null;
+                }
+            });
+
+        int v = getLower0();
+        if (v == -1) {
+            v = defaultLower;
+        }
+        lower = v;
+
+        v = getUpper0();
+        if (v == -1) {
+            v = defaultUpper;
+        }
+        upper = v;
+    }
+
+    static native int getLower0();
+    static native int getUpper0();
+
+    public static int getLower() {
+        return lower;
+    }
+
+    public static int getUpper() {
+        return upper;
+    }
+}
--- a/jdk/src/windows/classes/sun/nio/ch/WindowsAsynchronousSocketChannelImpl.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/src/windows/classes/sun/nio/ch/WindowsAsynchronousSocketChannelImpl.java	Fri Jan 10 15:04:46 2014 +0000
@@ -31,6 +31,9 @@
 import java.net.*;
 import java.util.concurrent.*;
 import java.io.IOException;
+import java.security.AccessController;
+import java.security.PrivilegedActionException;
+import java.security.PrivilegedExceptionAction;
 import sun.misc.Unsafe;
 
 /**
@@ -300,6 +303,19 @@
         }
     }
 
+    private void doPrivilegedBind(final SocketAddress sa) throws IOException {
+        try {
+            AccessController.doPrivileged(new PrivilegedExceptionAction<Void>() {
+                public Void run() throws IOException {
+                    bind(sa);
+                    return null;
+                }
+            });
+        } catch (PrivilegedActionException e) {
+            throw (IOException) e.getException();
+        }
+    }
+
     @Override
     <A> Future<Void> implConnect(SocketAddress remote,
                                  A attachment,
@@ -330,7 +346,12 @@
                 throw new ConnectionPendingException();
             if (localAddress == null) {
                 try {
-                    bind(new InetSocketAddress(0));
+                    SocketAddress any = new InetSocketAddress(0);
+                    if (sm == null) {
+                        bind(any);
+                    } else {
+                        doPrivilegedBind(any);
+                    }
                 } catch (IOException x) {
                     bindException = x;
                 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/windows/native/sun/net/portconfig.c	Fri Jan 10 15:04:46 2014 +0000
@@ -0,0 +1,107 @@
+/*
+ * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+#include <windows.h>
+#include "jni.h"
+#include "net_util.h"
+#include "sun_net_PortConfig.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+struct portrange {
+    int lower;
+    int higher;
+};
+
+static int getPortRange(struct portrange *range)
+{
+    OSVERSIONINFO ver;
+    ver.dwOSVersionInfoSize = sizeof(ver);
+    GetVersionEx(&ver);
+
+    /* Check for major version 5 or less = Windows XP/2003 or older */
+    if (ver.dwMajorVersion <= 5) {
+        LONG ret;
+        HKEY hKey;
+        range->lower = 1024;
+        range->higher = 4999;
+
+        /* check registry to see if upper limit was raised */
+        ret = RegOpenKeyEx(HKEY_LOCAL_MACHINE,
+                   "SYSTEM\\CurrentControlSet\\Services\\Tcpip\\Parameters",
+                   0, KEY_READ, (PHKEY)&hKey
+        );
+        if (ret == ERROR_SUCCESS) {
+            DWORD maxuserport;
+            ULONG ulType;
+            DWORD dwLen = sizeof(maxuserport);
+            ret = RegQueryValueEx(hKey, "MaxUserPort",  NULL, &ulType,
+                             (LPBYTE)&maxuserport, &dwLen);
+            RegCloseKey(hKey);
+            if (ret == ERROR_SUCCESS) {
+                range->higher = maxuserport;
+            }
+        }
+    } else {
+        /* There doesn't seem to be an API to access this. "MaxUserPort"
+          * is affected, but is not sufficient to determine.
+         * so we just use the defaults, which are less likely to change
+          */
+        range->lower = 49152;
+        range->higher = 65535;
+    }
+    return 0;
+}
+
+/*
+ * Class:     sun_net_PortConfig
+ * Method:    getLower0
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_sun_net_PortConfig_getLower0
+  (JNIEnv *env, jclass clazz)
+{
+    struct portrange range;
+    getPortRange(&range);
+    return range.lower;
+}
+
+/*
+ * Class:     sun_net_PortConfig
+ * Method:    getUpper0
+ * Signature: ()I
+ */
+JNIEXPORT jint JNICALL Java_sun_net_PortConfig_getUpper0
+  (JNIEnv *env, jclass clazz)
+{
+    struct portrange range;
+    getPortRange(&range);
+    return range.higher;
+}
+#ifdef __cplusplus
+}
+#endif
--- a/jdk/test/java/lang/SecurityManager/CheckPackageAccess.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/java/lang/SecurityManager/CheckPackageAccess.java	Fri Jan 10 15:04:46 2014 +0000
@@ -23,7 +23,7 @@
 
 /*
  *  @test
- *  @bug 6741606 7146431 8000450 8019830
+ *  @bug 6741606 7146431 8000450 8019830 8022945
  *  @summary Make sure all restricted packages listed in the package.access
  *           property in the java.security file are blocked
  *  @run main/othervm CheckPackageAccess
@@ -56,6 +56,7 @@
         "com.sun.istack.internal.",
         "com.sun.jmx.",
         "com.sun.media.sound.",
+        "com.sun.naming.internal.",
         "com.sun.proxy.",
         "com.sun.corba.se.",
         "com.sun.org.apache.bcel.internal.",
--- a/jdk/test/java/rmi/activation/rmidViaInheritedChannel/RmidViaInheritedChannel.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/java/rmi/activation/rmidViaInheritedChannel/RmidViaInheritedChannel.java	Fri Jan 10 15:04:46 2014 +0000
@@ -88,6 +88,17 @@
                                    TestLibrary.RMIDVIAINHERITEDCHANNEL_ACTIVATION_PORT);
             rmid.addOptions(new String[]{
                 "-Djava.nio.channels.spi.SelectorProvider=RmidViaInheritedChannel$RmidSelectorProvider"});
+            if (System.getProperty("os.name").startsWith("Windows") &&
+                System.getProperty("os.version").startsWith("5."))
+            {
+                /* Windows XP/2003 or older
+                 * Need to expand ephemeral range to include RMI test ports
+                 */
+                rmid.addOptions(new String[]{
+                    "-Djdk.net.ephemeralPortRange.low=1024",
+                    "-Djdk.net.ephemeralPortRange.high=64000"
+                });
+            }
             rmid.start();
 
             /*
--- a/jdk/test/java/rmi/registry/readTest/readTest.sh	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/java/rmi/registry/readTest/readTest.sh	Fri Jan 10 15:04:46 2014 +0000
@@ -29,6 +29,10 @@
 # @run shell readTest.sh
 
 OS=`uname -s`
+VER=`uname -r`
+ARGS=""
+REGARGS=""
+
 case "$OS" in
   SunOS | Linux | Darwin )
     PS=":"
@@ -39,11 +43,19 @@
     PS=";"
     FS="\\"
     FILEURL="file:/"
+    if [ "$VER" -eq "5" ]; then
+        ARGS="-Djdk.net.ephemeralPortRange.low=1024 -Djdk.net.ephemeralPortRange.high=65000"
+        REGARGS="-J-Djdk.net.ephemeralPortRange.low=1024 -J-Djdk.net.ephemeralPortRange.high=65000"
+    fi
     ;;
   CYGWIN* )
     PS=";"
     FS="/"
     FILEURL="file:/"
+    if [ "$VER" -eq "5" ]; then
+        ARGS="-Djdk.net.ephemeralPortRange.low=1024 -Djdk.net.ephemeralPortRange.high=65000"
+        REGARGS="-J-Djdk.net.ephemeralPortRange.low=1024 -J-Djdk.net.ephemeralPortRange.high=65000"
+    fi
     ;;
   * )
     echo "Unrecognized system!"
@@ -61,8 +73,8 @@
 #start rmiregistry without any local classes on classpath
 cd rmi_tmp
 # NOTE: This RMI Registry port must match TestLibrary.READTEST_REGISTRY_PORT
-${TESTJAVA}${FS}bin${FS}rmiregistry -J-Djava.rmi.server.useCodebaseOnly=false \
-    ${TESTTOOLVMOPTS} 64005 > ..${FS}${RMIREG_OUT} 2>&1 &
+${TESTJAVA}${FS}bin${FS}rmiregistry ${REGARGS} -J-Djava.rmi.server.useCodebaseOnly=false \
+    ${TESTTOOLVMOPTS} 60005 > ..${FS}${RMIREG_OUT} 2>&1 &
 RMIREG_PID=$!
 # allow some time to start
 sleep 3
@@ -74,10 +86,10 @@
     ;;
   * )
     CODEBASE=`pwd`
-    ;;  
+    ;;
 esac
 # trailing / after code base is important for rmi codebase property.
-${TESTJAVA}${FS}bin${FS}java ${TESTVMOPTS} -cp $TEST_CLASSPATH -Djava.rmi.server.codebase=${FILEURL}$CODEBASE/ readTest > OUT.TXT 2>&1 &
+${TESTJAVA}${FS}bin${FS}java ${TESTVMOPTS} -cp $TEST_CLASSPATH ${ARGS} -Djava.rmi.server.codebase=${FILEURL}$CODEBASE/ readTest > OUT.TXT 2>&1 &
 TEST_PID=$!
 #bulk of testcase - let it run for a while
 sleep 5
@@ -100,7 +112,7 @@
 result2=$?
 
 if [ $result1 -eq 0  -a $result2 -eq 0 ]
-then 
+then
     echo "Passed"
     exitCode=0;
 else
@@ -108,6 +120,6 @@
     exitCode=1
 fi
 rm -rf OUT.TXT ${RMIREG_OUT} rmi_tmp
-exit ${exitCode}    
+exit ${exitCode}
 
 
--- a/jdk/test/java/rmi/testlibrary/TestLibrary.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/java/rmi/testlibrary/TestLibrary.java	Fri Jan 10 15:04:46 2014 +0000
@@ -86,13 +86,13 @@
      * FIXED_PORT_MIN or above FIXED_PORT_MAX, then adjust
      * FIXED_PORT_MIN/MAX appropriately.
      */
-    public final static int FIXED_PORT_MIN = 64001;
-    public final static int FIXED_PORT_MAX = 64010;
-    public final static int RMIDVIAINHERITEDCHANNEL_ACTIVATION_PORT = 64001;
-    public final static int RMIDVIAINHERITEDCHANNEL_REGISTRY_PORT = 64002;
-    public final static int INHERITEDCHANNELNOTSERVERSOCKET_ACTIVATION_PORT = 64003;
-    public final static int INHERITEDCHANNELNOTSERVERSOCKET_REGISTRY_PORT = 64004;
-    public final static int READTEST_REGISTRY_PORT = 64005;
+    public final static int FIXED_PORT_MIN = 60001;
+    public final static int FIXED_PORT_MAX = 60010;
+    public final static int RMIDVIAINHERITEDCHANNEL_ACTIVATION_PORT = 60001;
+    public final static int RMIDVIAINHERITEDCHANNEL_REGISTRY_PORT = 60002;
+    public final static int INHERITEDCHANNELNOTSERVERSOCKET_ACTIVATION_PORT = 60003;
+    public final static int INHERITEDCHANNELNOTSERVERSOCKET_REGISTRY_PORT = 60004;
+    public final static int READTEST_REGISTRY_PORT = 60005;
     private final static int MAX_SERVER_SOCKET_TRIES = 2*(FIXED_PORT_MAX-FIXED_PORT_MIN+1);
 
     static void mesg(Object mesg) {
--- a/jdk/test/sun/security/tools/jarsigner/TimestampCheck.java	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/sun/security/tools/jarsigner/TimestampCheck.java	Fri Jan 10 15:04:46 2014 +0000
@@ -239,13 +239,13 @@
                 " -J-Djava.security.egd=file:/dev/./urandom" +
                 " -debug -keystore " + TSKS + " -storepass changeit" +
                 " -tsa http://localhost:" + port + "/%d" +
-                " -signedjar new.jar " + JAR + " old";
+                " -signedjar new_%d.jar " + JAR + " old";
         } else {
             cmd = System.getProperty("java.home") + "/bin/jarsigner" +
                 " -J-Djava.security.egd=file:/dev/./urandom" +
                 " -debug -keystore " + TSKS + " -storepass changeit" +
                 " -tsa http://localhost:" + port + "/%d" +
-                " -signedjar new.jar " + JAR + " old";
+                " -signedjar new_%d.jar " + JAR + " old";
         }
 
         try {
@@ -280,7 +280,7 @@
     static void jarsigner(String cmd, int path, boolean expected)
             throws Exception {
         System.err.println("Test " + path);
-        Process p = Runtime.getRuntime().exec(String.format(cmd, path));
+        Process p = Runtime.getRuntime().exec(String.format(cmd, path, path));
         BufferedReader reader = new BufferedReader(
                 new InputStreamReader(p.getErrorStream()));
         while (true) {
@@ -288,9 +288,25 @@
             if (s == null) break;
             System.err.println(s);
         }
+
+        // Will not see noTimestamp warning
+        boolean seeWarning = false;
+        reader = new BufferedReader(
+                new InputStreamReader(p.getInputStream()));
+        while (true) {
+            String s = reader.readLine();
+            if (s == null) break;
+            System.err.println(s);
+            if (s.indexOf("Warning:") >= 0) {
+                seeWarning = true;
+            }
+        }
         int result = p.waitFor();
         if (expected && result != 0 || !expected && result == 0) {
             throw new Exception("Failed");
         }
+        if (seeWarning) {
+            throw new Exception("See warning");
+        }
     }
 }
--- a/jdk/test/sun/security/tools/jarsigner/concise_jarsigner.sh	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/sun/security/tools/jarsigner/concise_jarsigner.sh	Fri Jan 10 15:04:46 2014 +0000
@@ -139,7 +139,6 @@
 # 16 and 32 already covered in the first part
 # ==========================================================
 
-$KT -genkeypair -alias expiring -dname CN=expiring -startdate -1m
 $KT -genkeypair -alias expired -dname CN=expired -startdate -10m
 $KT -genkeypair -alias notyetvalid -dname CN=notyetvalid -startdate +1m
 $KT -genkeypair -alias badku -dname CN=badku -ext KU=cRLSign -validity 365
@@ -154,9 +153,6 @@
         $KT -importcert -alias badchain
 $KT -delete -alias ca
 
-$JARSIGNER -strict -keystore js.jks -storepass changeit a.jar expiring
-[ $? = 2 ] || exit $LINENO
-
 $JARSIGNER -strict -keystore js.jks -storepass changeit a.jar expired
 [ $? = 4 ] || exit $LINENO
 
--- a/jdk/test/sun/security/tools/jarsigner/ts.sh	Fri Jan 10 15:51:24 2014 +0100
+++ b/jdk/test/sun/security/tools/jarsigner/ts.sh	Fri Jan 10 15:04:46 2014 +0000
@@ -22,7 +22,7 @@
 #
 
 # @test
-# @bug 6543842 6543440 6939248 8009636
+# @bug 6543842 6543440 6939248 8009636 8024302
 # @summary checking response of timestamp
 #
 # @run shell/timeout=600 ts.sh
@@ -53,7 +53,7 @@
 JAR="${TESTJAVA}${FS}bin${FS}jar"
 JAVA="${TESTJAVA}${FS}bin${FS}java"
 JAVAC="${TESTJAVA}${FS}bin${FS}javac"
-KT="${TESTJAVA}${FS}bin${FS}keytool -keystore tsks -storepass changeit -keypass changeit -keyalg rsa"
+KT="${TESTJAVA}${FS}bin${FS}keytool -keystore tsks -storepass changeit -keypass changeit -keyalg rsa -validity 200"
 
 rm tsks
 echo Nothing > A
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/test/sun/security/tools/jarsigner/warnings.sh	Fri Jan 10 15:04:46 2014 +0000
@@ -0,0 +1,119 @@
+#
+# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+#
+# This code is free software; you can redistribute it and/or modify it
+# under the terms of the GNU General Public License version 2 only, as
+# published by the Free Software Foundation.
+#
+# This code is distributed in the hope that it will be useful, but WITHOUT
+# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+# FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+# version 2 for more details (a copy is included in the LICENSE file that
+# accompanied this code).
+#
+# You should have received a copy of the GNU General Public License version
+# 2 along with this work; if not, write to the Free Software Foundation,
+# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+#
+# Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+# or visit www.oracle.com if you need additional information or have any
+# questions.
+#
+
+# @test
+# @bug 8024302
+# @bug 8026037
+# @summary Clarify jar verifications
+#
+
+if [ "${TESTJAVA}" = "" ] ; then
+  JAVAC_CMD=`which javac`
+  TESTJAVA=`dirname $JAVAC_CMD`/..
+fi
+
+# set platform-dependent variables
+OS=`uname -s`
+case "$OS" in
+  Windows_* )
+    FS="\\"
+    ;;
+  * )
+    FS="/"
+    ;;
+esac
+
+KS=warnings.jks
+JFILE=warnings.jar
+
+KT="$TESTJAVA${FS}bin${FS}keytool -storepass changeit -keypass changeit \
+        -keystore $KS"
+JAR=$TESTJAVA${FS}bin${FS}jar
+JARSIGNER="$TESTJAVA${FS}bin${FS}jarsigner -keystore $KS -storepass changeit"
+
+rm $KS 2> /dev/null
+
+LANG=C
+export LANG
+
+echo 12345 > file
+
+ERR=""
+
+# Normal signer expiring on 2100-01-01
+$KT -alias s1 -dname CN=s1 -genkey -startdate 2000/01/01 -validity 36525 || ERR="$ERR keytool s1,"
+# Cert expiring soon, informational warning
+$KT -alias s2 -dname CN=s2 -genkey -validity 100 || ERR="$ERR keytool s2,"
+# Cert expired, severe warning
+$KT -alias s3 -dname CN=s3 -genkey -startdate -200d -validity 100 || ERR="$ERR keytool s3,"
+
+# noTimestamp is informatiional warning and includes a date
+$JAR cvf $JFILE file
+$JARSIGNER $JFILE s1 > output1 || ERR="$ERR jarsigner s1,"
+$JARSIGNER -strict $JFILE s1 >> output1 || ERR="$ERR jarsigner s1 strict,"
+$JARSIGNER -verify $JFILE s1 >> output1 || ERR="$ERR jarsigner s1,"
+$JARSIGNER -verify -strict $JFILE s1 >> output1 || ERR="$ERR jarsigner s1 strict,"
+
+cat output1 | grep Warning || ERR="$ERR s1 warning,"
+cat output1 | grep Error && ERR="$ERR s1 error,"
+cat output1 | grep timestamp | grep 2100-01-01 || ERR="$ERR s1 timestamp,"
+cat output1 | grep "with signer errors" && ERR="$ERR s1 err,"
+
+# hasExpiringCert is informatiional warning
+$JAR cvf $JFILE file
+$JARSIGNER $JFILE s2 > output2 || ERR="$ERR jarsigner s2,"
+$JARSIGNER -strict $JFILE s2 >> output2 || ERR="$ERR jarsigner s2 strict,"
+$JARSIGNER -verify $JFILE s2 >> output2 || ERR="$ERR jarsigner s2,"
+$JARSIGNER -verify -strict $JFILE s2 >> output2 || ERR="$ERR jarsigner s2 strict,"
+
+cat output2 | grep Warning || ERR="$ERR s2 warning,"
+cat output2 | grep Error && ERR="$ERR s2 error,"
+cat output2 | grep timestamp || ERR="$ERR s2 timestamp,"
+cat output2 | grep "will expire" || ERR="$ERR s2 expiring,"
+cat output2 | grep "with signer errors" && ERR="$ERR s2 err,"
+
+# hasExpiredCert is severe warning
+$JAR cvf $JFILE file
+$JARSIGNER $JFILE s3 > output3 || ERR="$ERR jarsigner s3,"
+$JARSIGNER -strict $JFILE s3 > output3s && ERR="$ERR jarsigner s3 strict,"
+$JARSIGNER -verify $JFILE s3 >> output3 || ERR="$ERR jarsigner s3,"
+$JARSIGNER -verify -strict $JFILE s3 >> output3s && ERR="$ERR jarsigner s3 strict,"
+
+# warning without -strict
+cat output3 | grep Warning || ERR="$ERR s3 warning,"
+cat output3 | grep Error && ERR="$ERR s3 error,"
+cat output3 | grep "with signer errors" && ERR="$ERR s3 err,"
+
+# error with -strict
+cat output3s | grep Warning || ERR="$ERR s3s warning,"
+cat output3s | grep Error || ERR="$ERR s3s error,"
+cat output3s | grep "with signer errors" || ERR="$ERR s3 err,"
+
+if [ "$ERR" = "" ]; then
+    exit 0
+else
+    echo "ERR is $ERR"
+    exit 1
+fi
+
+