changeset 6080:4770b0a49675

Merge
author mullan
date Mon, 05 Nov 2012 10:33:18 -0500
parents 46b24eb85b86 (current diff) 8b944ebef8a7 (diff)
children 510cb3671f14
files make/sun/jdbc/Makefile src/share/classes/sun/net/www/protocol/gopher/GopherClient.java src/share/classes/sun/net/www/protocol/gopher/Handler.java src/solaris/native/java/io/FileSystem_md.c src/windows/native/java/io/FileSystem_md.c
diffstat 399 files changed, 50160 insertions(+), 6248 deletions(-) [+]
line wrap: on
line diff
--- a/.hgtags	Mon Nov 05 10:30:49 2012 -0500
+++ b/.hgtags	Mon Nov 05 10:33:18 2012 -0500
@@ -182,3 +182,5 @@
 d94613ac03d8de375ef60493e2bb76dbd30d875d jdk8-b58
 abad1f417bd3df4296631fc943cd3b7f5062c88a jdk8-b59
 cec8fa02f15634acd7d02d04b0b2d8c044cdbaaa jdk8-b60
+61ddb3fd000a09ab05bff1940b0ac211661e94cf jdk8-b61
+50b8b17449d200c66bfd68fb4f3a9197432c9e2b jdk8-b62
--- a/THIRD_PARTY_README	Mon Nov 05 10:30:49 2012 -0500
+++ b/THIRD_PARTY_README	Mon Nov 05 10:33:18 2012 -0500
@@ -2,11 +2,11 @@
 -----------------------------
 
 %% This notice is provided with respect to ASM Bytecode Manipulation 
-Framework v3.1, which is included with JRE 7, JDK 7, and OpenJDK 7.
+Framework v4.0, which is included with JRE 8, and JDK 8.
 
 --- begin of LICENSE ---
 
-Copyright (c) 2000-2005 INRIA, France Telecom
+Copyright (c) 2000-2011 France Télécom
 All rights reserved.
 
 Redistribution and use in source and binary forms, with or without
--- a/make/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -233,7 +233,7 @@
 
 all build:: sanity-all post-sanity-all
 
-SUBDIRS       = tools java javax sun com
+SUBDIRS       = tools java javax sun com jdk
 ifeq ($(PLATFORM), macosx)
   SUBDIRS += apple
 endif
--- a/make/com/oracle/security/ucrypto/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/com/oracle/security/ucrypto/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -198,9 +198,9 @@
   #
   # Build ucrypto.jar.
   #
-  $(UNSIGNED_DIR)/ucrypto.jar: build
+  $(UNSIGNED_DIR)/ucrypto.jar: build $(JCE_MANIFEST_FILE)
 	$(prep-target)
-	$(BOOT_JAR_CMD) cf $@ $(JAR_DIRS) \
+	$(BOOT_JAR_CMD) cmf $(JCE_MANIFEST_FILE) $@ $(JAR_DIRS) \
 	    $(BOOT_JAR_JFLAGS)
 	@$(java-vm-cleanup)
 
--- a/make/com/sun/java/pack/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/com/sun/java/pack/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -94,9 +94,9 @@
   LDOUTPUT = -Fe
 
   # JDK name required here
-  RC_FLAGS += /D "JDK_FNAME=$(PGRM).exe" \
-	/D "JDK_INTERNAL_NAME=$(PGRM)" \
-	/D "JDK_FTYPE=0x1L"
+  RC_FLAGS += -D "JDK_FNAME=$(PGRM).exe" \
+	-D "JDK_INTERNAL_NAME=$(PGRM)" \
+	-D "JDK_FTYPE=0x1L"
 
   RES = $(OBJDIR)/$(PGRM).res
 else
@@ -161,7 +161,7 @@
 	$(CP) mapfile-vers-unpack200 $(TEMPDIR)/mapfile-vers
 	$(LINKER)  $(LDDFLAGS) $(sort $(UNPACK_EXE_FILES_o)) $(RES) $(LIBCXX) $(LDOUTPUT)$(TEMPDIR)/unpack200$(EXE_SUFFIX)
 ifdef MT
-	$(MT) /manifest $(OBJDIR)/unpack200$(EXE_SUFFIX).manifest /outputresource:$(TEMPDIR)/unpack200$(EXE_SUFFIX);#1
+	$(MT) -manifest $(OBJDIR)/unpack200$(EXE_SUFFIX).manifest -outputresource:$(TEMPDIR)/unpack200$(EXE_SUFFIX);#1
 endif
 	$(CP) $(TEMPDIR)/unpack200$(EXE_SUFFIX) $(UNPACK_EXE)
 	@$(call binary_file_verification,$@)
--- a/make/common/Defs-windows.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/Defs-windows.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -78,7 +78,7 @@
   MS_RUNTIME_LIBRARIES = $(MSVCRNN_DLL)
 endif
 
-EXTRA_LFLAGS += /LIBPATH:$(DXSDK_LIB_PATH)
+EXTRA_LFLAGS += -LIBPATH:$(DXSDK_LIB_PATH)
 
 # Full Debug Symbols has been enabled on Windows since JDK1.4.1.
 # The Full Debug Symbols (FDS) default for VARIANT == OPT builds is
@@ -198,7 +198,7 @@
 #   -MTd       Use static debug version (better than -MDd, no runtime issues)
 #   -D_DEBUG   Change use of malloc/free/etc to use special debug ones (-MTd)
 #
-#      NOTE: We also will use /D _STATIC_CPPLIB  so we don't need msvcpnn.dll
+#      NOTE: We also will use -D _STATIC_CPPLIB  so we don't need msvcpnn.dll
 #
 # If MS_RUNTIME_STATIC is requested we may have a problem, it is no longer
 #     supported by VS2010
@@ -223,12 +223,12 @@
 endif
 
 # Always add _STATIC_CPPLIB definition
-STATIC_CPPLIB_OPTION = /D _STATIC_CPPLIB
+STATIC_CPPLIB_OPTION = -D _STATIC_CPPLIB
 
 # Silence the warning about using _STATIC_CPPLIB
 ifneq ($(SHOW_ALL_WARNINGS),true)
   # Needed with VS2010 to turn off the deprecated warning.
-  STATIC_CPPLIB_OPTION += /D _DISABLE_DEPRECATE_STATIC_CPPLIB
+  STATIC_CPPLIB_OPTION += -D _DISABLE_DEPRECATE_STATIC_CPPLIB
 endif
 
 MS_RUNTIME_OPTION += $(STATIC_CPPLIB_OPTION)
@@ -242,7 +242,7 @@
   #   -Od      Turns off optimization and speeds compilation
   #   -YX -Fp/.../foobar.pch   Use precompiled headers (try someday?)
   #   -nologo  Don't print out startup message
-  #   /D _STATIC_CPPLIB
+  #  -D _STATIC_CPPLIB
   #            Use static link for the C++ runtime (so msvcpnn.dll not needed)
   #   
   ifeq ($(ENABLE_FULL_DEBUG_SYMBOLS),1)
@@ -258,12 +258,12 @@
   CFLAGS_COMMON += $(MS_RUNTIME_OPTION) $(CFLAGS_$(COMPILER_VERSION))
 
   ifeq ($(ENABLE_FULL_DEBUG_SYMBOLS),1)
-    LDEBUG = /debug
+    LDEBUG = -debug
   endif
   
   ifeq ($(VTUNE_SUPPORT), true)
     OTHER_CFLAGS = -Z7 -Ox 
-    LDEBUG += /pdb:NONE
+    LDEBUG += -pdb:NONE
   endif
   
   # VS2010, always need safe exception handlers, not needed on 64bit
@@ -272,7 +272,7 @@
   endif
 
   # LFLAGS are the flags given to $(LINK) and used to build the actual DLL file
-  BASELFLAGS = -nologo /opt:REF /incremental:no
+  BASELFLAGS = -nologo -opt:REF -incremental:no
 
   LFLAGS = $(BASELFLAGS) $(LDEBUG) $(EXTRA_LFLAGS) $(LFLAGS_$(COMPILER_VERSION))
   LDDFLAGS += $(LFLAGS_$(COMPILER_VERSION))
@@ -404,7 +404,7 @@
   JDK_UPDATE_VER := 0
 endif
 
-RC_FLAGS = /l 0x409 /r
+RC_FLAGS = -l 0x409 -r
 
 ifeq ($(VARIANT), OPT)
   RC_FLAGS += -d NDEBUG 
--- a/make/common/Demo.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/Demo.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -292,9 +292,9 @@
 
 ifeq ($(PLATFORM),windows)
 # JDK name required here
-RC_FLAGS += /D "JDK_FNAME=$(LIBRARY).dll" \
-            /D "JDK_INTERNAL_NAME=$(LIBRARY)" \
-            /D "JDK_FTYPE=0x2L"
+RC_FLAGS += -D "JDK_FNAME=$(LIBRARY).dll" \
+            -D "JDK_INTERNAL_NAME=$(LIBRARY)" \
+            -D "JDK_FTYPE=0x2L"
 endif
 
 # Native library building
--- a/make/common/Library.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/Library.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -206,9 +206,9 @@
 	@$(ECHO) Created $@ 
 
 # JDK name required here
-RC_FLAGS += /D "JDK_FNAME=$(LIBRARY).dll" \
-            /D "JDK_INTERNAL_NAME=$(LIBRARY)" \
-            /D "JDK_FTYPE=0x2L"
+RC_FLAGS += -D "JDK_FNAME=$(LIBRARY).dll" \
+            -D "JDK_INTERNAL_NAME=$(LIBRARY)" \
+            -D "JDK_FTYPE=0x2L"
 
 $(OBJDIR)/$(LIBRARY).res: $(VERSIONINFO_RESOURCE)
 ifndef LOCAL_RESOURCE_FILE
--- a/make/common/Program.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/Program.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -157,9 +157,9 @@
 #
 ifeq ($(PLATFORM), windows)
   # JDK name required here
-  RC_FLAGS += /D "JDK_FNAME=$(PROGRAM)$(EXE_SUFFIX)" \
-              /D "JDK_INTERNAL_NAME=$(PROGRAM)" \
-              /D "JDK_FTYPE=0x1L"
+  RC_FLAGS += -D "JDK_FNAME=$(PROGRAM)$(EXE_SUFFIX)" \
+              -D "JDK_INTERNAL_NAME=$(PROGRAM)" \
+              -D "JDK_FTYPE=0x1L"
 
   $(OBJDIR)/$(PROGRAM).res: $(VERSIONINFO_RESOURCE)
 	@$(prep-target)
@@ -201,11 +201,11 @@
 	@$(prep-target)
 	@set -- $?; \
 	    $(ECHO) Rebuilding $@ because of $$1 $$2 $$3 $$4 $$5 $$6 $${7:+...};
-	$(LINK) -out:$@ /STACK:$(STACK_SIZE) \
+	$(LINK) -out:$@ -STACK:$(STACK_SIZE) \
 	    $(MAP_OPTION) $(LFLAGS) $(LDFLAGS) \
 	    @$(OBJDIR)/$(PROGRAM).lcf $(LDLIBS)
   ifdef MT
-	$(MT) /manifest $(OBJDIR)/$(PROGRAM).exe.manifest /outputresource:$@;#1
+	$(MT) -manifest $(OBJDIR)/$(PROGRAM).exe.manifest /outputresource:$@;#1
   endif
 	@$(call binary_file_verification,$@)
   ifeq ($(ENABLE_FULL_DEBUG_SYMBOLS),1)
--- a/make/common/Release.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/Release.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -784,11 +784,22 @@
 		    $(RT_JAR) $(RESOURCES_JAR) $(JSSE_JAR) $(JFR_JAR) \
 		    $(BUILDMETAINDEX_JARFILE)
 	@# Copy in bin directory
+ifeq ($(USING_MSYS),true)
+        # No cpio in MinGW/MSYS
+	$(CD) $(OUTPUTDIR) && $(TAR) -cf - bin | ($(CD) $(JRE_IMAGE_DIR) && $(TAR) -xpf -)
+else
 	$(CD) $(OUTPUTDIR) && $(FIND) bin -depth | $(CPIO) -pdum $(JRE_IMAGE_DIR)
+endif
 	@# CTE plugin security change require new empty directory lib/applet
 	$(MKDIR) -p $(JRE_IMAGE_DIR)/lib/applet
 	@# Copy in lib directory
+ifeq ($(USING_MSYS),true)
+        # No cpio in MinGW/MSYS
+	$(CD) $(OUTPUTDIR) && $(TAR) -cf - lib | ($(CD) $(JRE_IMAGE_DIR) && $(TAR) -xpf -)
+else
 	$(CD) $(OUTPUTDIR) && $(FIND) lib -depth | $(CPIO) -pdum $(JRE_IMAGE_DIR)
+endif
+
   ifeq ($(USING_CYGWIN),true)
 	  $(RM) -rf $(JRE_IMAGE_DIR)/[A-Za-z]:
 	  $(RM) -rf $(OUTPUTDIR)/[A-Za-z]:
@@ -919,11 +930,17 @@
 # only places from which we copy everything), but because the presence
 # of this file causes cygwin's find to bomb out, thus breaking the build
 # in "install".
+
 initial-image-jdk-setup:
 	$(RM) -r $(JDK_IMAGE_DIR)
 	$(MKDIR) -p $(JDK_IMAGE_DIR)/jre
+ifeq ($(USING_MSYS),true)
+	($(CD) $(JRE_IMAGE_DIR) && $(TAR) -cf - . \
+	      | ($(CD) $(JDK_IMAGE_DIR)/jre && $(TAR) -xpf -))
+else
 	($(CD) $(JRE_IMAGE_DIR) && $(FIND) . -depth -print \
 	      | $(CPIO) -pdum $(JDK_IMAGE_DIR)/jre )
+endif
   ifeq ($(USING_CYGWIN),true)
 	  $(RM) -rf $(JRE_IMAGE_DIR)/[A-Za-z]:
 	  $(RM) -rf $(JDK_IMAGE_DIR)/jre/[A-Za-z]:
--- a/make/common/Sanity.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/Sanity.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -64,7 +64,6 @@
     sane-math_iso \
     sane-libCrun \
     sane-unixccs_path \
-    sane-odbcdir \
     sane-msdevtools_path \
     sane-dxsdk \
     sane-compiler \
--- a/make/common/shared/Defs-solaris.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/shared/Defs-solaris.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -206,13 +206,12 @@
 #     libjdgaSUNWffb.so
 #     libjdgaSUNWm64.so
 #     libxinerama.so
-#   The library libJdbcOdbc.so has also been given an exception.
 #   The JNI/JVMTI demo libraries are also missing mapfiles, no exceptions yet.
 ifeq ($(ARCH_FAMILY),sparc)
   MAPFILE_EXCEPTIONS = \
-    (libJdbcOdbc|libjdgaSUNWafb|libjdgaSUNWcg6|libjdgaSUNWffb|libjdgaSUNWm64|libxinerama)
+    (libjdgaSUNWafb|libjdgaSUNWcg6|libjdgaSUNWffb|libjdgaSUNWm64|libxinerama)
 else
-  MAPFILE_EXCEPTIONS = (libJdbcOdbc)
+  MAPFILE_EXCEPTIONS = ()
 endif
 
 # Macro to check it's input file for banned dependencies and verify the
--- a/make/common/shared/Defs-utils.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/shared/Defs-utils.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -169,15 +169,19 @@
 ifeq ($(PLATFORM),windows)
   ifdef USING_CYGWIN
     # Intrinsic unix command, with backslash-escaped character interpretation
-    ECHO = $(UNIXCOMMAND_PATH)echo -e
-    ZIPEXE = $(UNIXCOMMAND_PATH)zip
-    UNZIP  = $(UNIXCOMMAND_PATH)unzip
+    ECHO     = $(UNIXCOMMAND_PATH)echo -e
+    ZIPEXE   = $(UNIXCOMMAND_PATH)zip
+    UNZIP    = $(UNIXCOMMAND_PATH)unzip
     # Some CYGWIN nawk versions require BINMODE=w for proper '\r' interpretation
-    NAWK   = $(UNIXCOMMAND_PATH)awk -v BINMODE=w
+    NAWK     = $(UNIXCOMMAND_PATH)awk -v BINMODE=w
   else
     ZIPEXE = $(UTILS_DEVTOOL_PATH)zip
     UNZIP  = $(UTILS_DEVTOOL_PATH)unzip
     NAWK   = $(UNIXCOMMAND_PATH)awk
+    ifdef USING_MSYS
+      ECHO   = $(UTILS_COMMAND_PATH)echo -e
+      AR     = $(UTILS_DEVTOOL_PATH)ar
+    endif
   endif
   # Re-define some utilities
   LEX            =# override GNU Make intrinsic: no lex on windows
--- a/make/common/shared/Defs-windows.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/shared/Defs-windows.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -112,6 +112,15 @@
 $(shell if [ "$1" != "" -a -d "$1" ]; then $(CYGPATH_CMD) "$1" 2> $(DEV_NULL); else echo "$1"; fi)
 endef
 else
+ifdef USING_MSYS
+DOSPATH_CMD:=$(shell cd $(JDK_TOPDIR) 2> $(DEV_NULL) && pwd)/make/tools/msys_build_scripts/dospath.sh
+define FullPath
+$(subst \,/,$(shell $(DOSPATH_CMD) $1))
+endef
+define OptFullPath
+$(shell if [ "$1" != "" -a -d "$1" ]; then (cd $1 && pwd); else echo "$1"; fi)
+endef
+else
 # Temporary until we upgrade to MKS 8.7, MKS pwd returns mixed mode path
 define FullPath
 $(shell cd $1 2> $(DEV_NULL) && pwd)
@@ -120,6 +129,7 @@
 $(shell if [ "$1" != "" -a -d "$1" ]; then (cd $1 && pwd); else echo "$1"; fi)
 endef
 endif
+endif
 
 # System drive
 ifdef SYSTEMDRIVE
@@ -146,43 +156,47 @@
   ifdef USING_CYGWIN
     UNIXCOMMAND_PATH :=$(call PrefixPath,/usr/bin)
   else
-    ifdef ROOTDIR
-      xROOTDIR :="$(subst \,/,$(ROOTDIR))"
-      _rootdir :=$(call FullPath,$(xROOTDIR))
+    ifdef USING_MSYS
+      UNIXCOMMAND_PATH :=$(call PrefixPath,/bin)
     else
-      xROOTDIR :="$(_system_drive)/mksnt"
-      _rootdir :=$(call FullPath,$(xROOTDIR))
-    endif
-    ifneq ($(_rootdir),)
-      UNIXCOMMAND_PATH :=$(call PrefixPath,$(_rootdir)/mksnt)
-    endif
-  endif
+      ifdef ROOTDIR
+        xROOTDIR :="$(subst \,/,$(ROOTDIR))"
+        _rootdir :=$(call FullPath,$(xROOTDIR))
+      else
+        xROOTDIR :="$(_system_drive)/mksnt"
+        _rootdir :=$(call FullPath,$(xROOTDIR))
+      endif
+      ifneq ($(_rootdir),)
+        UNIXCOMMAND_PATH :=$(call PrefixPath,$(_rootdir)/mksnt)
+      endif
+    endif # USING_MSYS
+  endif # USING_CYGWIN
 endif
 UNIXCOMMAND_PATH:=$(call AltCheckSpaces,UNIXCOMMAND_PATH)
 
 # Get version of MKS or CYGWIN
-ifndef USING_CYGWIN
-_MKS_VER :=$(shell $(MKSINFO) 2>&1 | $(GREP) Release | $(TAIL) -1 | $(SED) -e 's@.*\(Release.*\)@\1@')
-MKS_VER  :=$(call GetVersion,$(_MKS_VER))
-# At this point, we can re-define FullPath to use DOSNAME_CMD
-CHECK_MKS87:=$(call CheckVersions,$(MKS_VER),8.7)
-TRY_DOSNAME:=false
-ifeq ($(CHECK_MKS87),same)
-TRY_DOSNAME:=true
-endif
-# Newer should be ok
-ifeq ($(CHECK_MKS87),newer)
-TRY_DOSNAME:=true
-endif
-ifeq ($(TRY_DOSNAME),true)
-ifeq ($(shell $(UNIXCOMMAND_PATH)dosname -s $(_system_drive)/ 2> $(DEV_NULL)),$(_system_drive)/)
-_DOSNAME=$(UNIXCOMMAND_PATH)dosname
-DOSNAME_CMD:=$(_DOSNAME) -s
+ifdef USING_MKS
+  _MKS_VER :=$(shell $(MKSINFO) 2>&1 | $(GREP) Release | $(TAIL) -1 | $(SED) -e 's@.*\(Release.*\)@\1@')
+  MKS_VER  :=$(call GetVersion,$(_MKS_VER))
+  # At this point, we can re-define FullPath to use DOSNAME_CMD
+  CHECK_MKS87:=$(call CheckVersions,$(MKS_VER),8.7)
+  TRY_DOSNAME:=false
+  ifeq ($(CHECK_MKS87),same)
+    TRY_DOSNAME:=true
+  endif
+  # Newer should be ok
+  ifeq ($(CHECK_MKS87),newer)
+    TRY_DOSNAME:=true
+  endif
+  ifeq ($(TRY_DOSNAME),true)
+    ifeq ($(shell $(UNIXCOMMAND_PATH)dosname -s $(_system_drive)/ 2> $(DEV_NULL)),$(_system_drive)/)
+      _DOSNAME=$(UNIXCOMMAND_PATH)dosname
+      DOSNAME_CMD:=$(_DOSNAME) -s
 define FullPath
 $(subst //,/,$(shell echo $1 | $(DOSNAME_CMD) 2> $(DEV_NULL)))
 endef
-endif # test dosname -s
-endif # TRY_DOSNAME
+    endif # test dosname -s
+  endif # TRY_DOSNAME
 endif # MKS
 
 # We try to get references to what we need via the default component
@@ -440,10 +454,14 @@
   ifdef USING_CYGWIN
     DEVTOOLS_PATH :=$(UNIXCOMMAND_PATH)
   else
-    xDEVTOOLS_PATH  :="$(_system_drive)/utils"
-    fxDEVTOOLS_PATH :=$(call FullPath,$(xDEVTOOLS_PATH))
-    DEVTOOLS_PATH  :=$(call PrefixPath,$(fxDEVTOOLS_PATH))
-  endif
+    ifdef USING_MSYS
+      DEVTOOLS_PATH :=$(UNIXCOMMAND_PATH)
+    else
+      xDEVTOOLS_PATH  :="$(_system_drive)/utils"
+      fxDEVTOOLS_PATH :=$(call FullPath,$(xDEVTOOLS_PATH))
+      DEVTOOLS_PATH  :=$(call PrefixPath,$(fxDEVTOOLS_PATH))
+    endif # USING_MSYS
+  endif # USING_CYGWIN
 endif
 DEVTOOLS_PATH:=$(call AltCheckSpaces,DEVTOOLS_PATH)
 
@@ -636,7 +654,7 @@
 
 # Special define for checking the binaries
 
-# All windows dll and exe files should have been built with /NXCOMPAT
+# All windows dll and exe files should have been built with -NXCOMPAT
 #   and be setup for dynamic base addresses.
 #   In addition, we should not be dependent on certain dll files that
 #   we do not or cannot redistribute.
@@ -648,37 +666,37 @@
   BANNED_DLLS=msvcp100[.]dll|msvcr100d[.]dll|msvcrtd[.]dll
 endif
 
-# Check for /safeseh (only used on 32bit)
+# Check for -safeseh (only used on 32bit)
 define binary_file_safeseh_verification # binary_file
 ( \
-  $(ECHO) "Checking for /SAFESEH usage in: $1" && \
-  if [ "`$(DUMPBIN) /loadconfig $1 | $(EGREP) -i 'Safe Exception Handler Table'`" = "" ] ; then \
+  $(ECHO) "Checking for -SAFESEH usage in: $1" && \
+  if [ "`$(DUMPBIN) -loadconfig $1 | $(EGREP) -i 'Safe Exception Handler Table'`" = "" ] ; then \
     $(ECHO) "ERROR: Did not find 'Safe Exception Handler Table' in loadconfig: $1" ; \
-    $(DUMPBIN) /loadconfig $1 ; \
+    $(DUMPBIN) -loadconfig $1 ; \
     exit 6 ; \
   fi ; \
 )
 endef
 
-# Check for /NXCOMPAT usage
+# Check for -NXCOMPAT usage
 define binary_file_nxcompat_verification # binary_file
 ( \
-  $(ECHO) "Checking for /NXCOMPAT usage in: $1" && \
-  if [ "`$(DUMPBIN) /headers $1 | $(EGREP) -i 'NX compatible'`" = "" ] ; then \
+  $(ECHO) "Checking for -NXCOMPAT usage in: $1" && \
+  if [ "`$(DUMPBIN) -headers $1 | $(EGREP) -i 'NX compatible'`" = "" ] ; then \
     $(ECHO) "ERROR: Did not find 'NX compatible' in headers: $1" ; \
-    $(DUMPBIN) /headers $1 ; \
+    $(DUMPBIN) -headers $1 ; \
     exit 7 ; \
   fi ; \
 )
 endef
 
-# Check for /DYNAMICBASE usage
+# Check for -DYNAMICBASE usage
 define binary_file_dynamicbase_verification # binary_file
 ( \
-  $(ECHO) "Checking for /DYNAMICBASE usage in: $1" && \
-  if [ "`$(DUMPBIN) /headers $1 | $(EGREP) -i 'Dynamic base'`" = "" ] ; then \
+  $(ECHO) "Checking for -DYNAMICBASE usage in: $1" && \
+  if [ "`$(DUMPBIN) -headers $1 | $(EGREP) -i 'Dynamic base'`" = "" ] ; then \
     $(ECHO) "ERROR: Did not find 'Dynamic base' in headers: $1" ; \
-    $(DUMPBIN) /headers $1 ; \
+    $(DUMPBIN) -headers $1 ; \
     exit 8 ; \
   fi ; \
 )
@@ -688,9 +706,9 @@
 define binary_file_dll_verification # binary_file
 ( \
   $(ECHO) "Checking for banned dependencies in: $1" && \
-  if [ "`$(DUMPBIN) /dependents $1 | $(EGREP) -i '$(BANNED_DLLS)'`" != "" ] ; then \
+  if [ "`$(DUMPBIN) -dependents $1 | $(EGREP) -i '$(BANNED_DLLS)'`" != "" ] ; then \
     $(ECHO) "ERROR: Found use of $(BANNED_DLLS)"; \
-    $(DUMPBIN) /dependents $1 ; \
+    $(DUMPBIN) -dependents $1 ; \
     exit 9 ; \
   fi ; \
 )
--- a/make/common/shared/Platform.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/shared/Platform.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -70,6 +70,8 @@
 #     LIBARCH32                   solaris only: sparc or i386
 #     LIBARCH64                   solaris only: sparcv9 or amd64
 #     USING_CYGWIN                windows only: true or false
+#     USING_MSYS                  windows only: true or false
+#     USING_MKS                   windows only: true or false
 #     ISHIELD_TEMP_MIN            windows only: minimum disk space in temp area
 
 # Only run uname once in this make session.
@@ -306,6 +308,8 @@
 # Windows with and without CYGWIN will be slightly different
 ifeq ($(SYSTEM_UNAME), Windows_NT)
   PLATFORM = windows
+  USING_MKS = true
+  export USING_MKS
 endif
 ifneq (,$(findstring CYGWIN,$(SYSTEM_UNAME)))
   PLATFORM = windows
@@ -318,6 +322,11 @@
     export CYGWIN_HOME
   endif
 endif
+ifneq (,$(findstring MINGW,$(SYSTEM_UNAME)))
+  PLATFORM = windows
+  USING_MSYS = true
+  export USING_MSYS
+endif
 
 # Platform settings specific to Windows
 ifeq ($(PLATFORM), windows)
@@ -395,11 +404,12 @@
   endif
   ARCH_FAMILY = $(ARCH)
   # Where is unwanted output to be delivered?
-  # MKS uses the special file "NUL", cygwin uses the customary unix file.
-  ifeq ($(USING_CYGWIN),true)
+  # MKS uses the special file "NUL"; Cygwin and MinGW/MSYS use the
+  # customary unix file.
+  ifeq ($(USING_MKS),true)
+    DEV_NULL = NUL
+  else
     DEV_NULL = /dev/null
-  else
-    DEV_NULL = NUL
   endif
   export DEV_NULL
   # Classpath separator
@@ -440,28 +450,11 @@
       _MB_OF_MEMORY := \
 	   $(shell free -m | grep Mem: | awk '{print $$2;}' )
     else
-      # Windows 2000 has the mem utility, but two memory areas
-      #    extended memory is what is beyond 1024M
-      _B_OF_EXT_MEMORY := \
-	   $(shell mem 2> $(DEV_NULL) | \
-		   grep 'total contiguous extended memory' | awk '{print $$1;}')
-      ifeq ($(_B_OF_EXT_MEMORY),)
-          _B_OF_MEMORY := \
-	   $(shell mem 2> $(DEV_NULL) | \
-		   grep 'total conventional memory' | awk '{print $$1;}')
-      else
-        _B_OF_MEMORY := \
-           $(shell expr 1048576 '+' $(_B_OF_EXT_MEMORY) 2> $(DEV_NULL))
-      endif
-      ifeq ($(_B_OF_MEMORY),)
-        # Windows 2003 has the systeminfo utility use it if mem doesn't work
-        _MB_OF_MEMORY := \
-	    $(shell systeminfo 2> $(DEV_NULL) | \
-		    grep 'Total Physical Memory:' | \
-		    awk '{print $$4;}' | sed -e 's@,@@')
-      else
-        _MB_OF_MEMORY := $(shell expr $(_B_OF_MEMORY) '/' 1024 2> $(DEV_NULL))
-      endif
+      # Windows XP and higher has the systeminfo utility
+      _MB_OF_MEMORY := \
+            $(shell systeminfo 2> $(DEV_NULL) | \
+                    grep 'Total Physical Memory:' | \
+                    awk '{print $$4;}' | sed -e 's@,@@')
     endif
     ifeq ($(shell expr $(_MB_OF_MEMORY) '+' 0 2> $(DEV_NULL)), $(_MB_OF_MEMORY))
       MB_OF_MEMORY := $(_MB_OF_MEMORY)
--- a/make/common/shared/Sanity-Settings.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/shared/Sanity-Settings.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -182,8 +182,13 @@
     ALL_SETTINGS+=$(call addRequiredVersionSetting,CYGWIN_VER)
     ALL_SETTINGS+=$(call addRequiredSetting,CYGPATH_CMD)
   else
-    ALL_SETTINGS+=$(call addRequiredVersionSetting,MKS_VER)
-    ALL_SETTINGS+=$(call addOptionalSetting,DOSNAME_CMD)
+    ifdef USING_MSYS
+      ALL_SETTINGS+=$(call addRequiredSetting,USING_MSYS)
+      ALL_SETTINGS+=$(call addRequiredSetting,DOSPATH_CMD)
+    else
+      ALL_SETTINGS+=$(call addRequiredVersionSetting,MKS_VER)
+      ALL_SETTINGS+=$(call addOptionalSetting,DOSNAME_CMD)
+    endif
   endif
 endif
 ifeq ($(PLATFORM),linux)
--- a/make/common/shared/Sanity.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/common/shared/Sanity.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -208,7 +208,6 @@
 	sane-docs_import \
 	sane-math_iso \
 	sane-libCrun \
-	sane-odbcdir \
 	sane-msdevtools_path \
 	sane-hotspot_binaries \
 	sane-hotspot_import \
@@ -395,7 +394,7 @@
 ifeq ($(PLATFORM), windows)
     MKS_CHECK :=$(call CheckVersions,$(MKS_VER),$(REQUIRED_MKS_VER))
 sane-mks:
-  ifndef USING_CYGWIN
+  ifdef USING_MKS
     ifeq ($(MKS_CHECK),missing)
 	@$(call OfficialErrorMessage,MKS version,$(MKS_VER),$(REQUIRED_MKS_VER))
     endif
@@ -905,14 +904,25 @@
 	    "" >> $(ERROR_FILE) ; \
 	fi
 ifeq ($(PLATFORM), windows)
-	@for utility in cpio ar file m4 ; do \
+ifeq ($(USING_MSYS), true)
+	@for utility in $(AR) $(FILE) $(M4) ; do \
 	  if [ ! -r "`$(WHICH) $${utility}`" ]; then \
 	    $(ECHO) "WARNING: You do not have the utility $${utility} in the \n" \
 	      "      directory $(UNIXCOMMAND_PATH). \n" \
-	      "      The utilities cpio, ar, file, and m4 are required. \n" \
+	      "      The utilities ar, file and m4 are required. \n" \
 	      "" >> $(WARNING_FILE) ; \
 	  fi; \
 	done
+else
+	@for utility in $(AR) $(CPIO) $(FILE) $(M4) ; do \
+	  if [ ! -r "`$(WHICH) $${utility}`" ]; then \
+	    $(ECHO) "WARNING: You do not have the utility $${utility} in the \n" \
+	      "      directory $(UNIXCOMMAND_PATH). \n" \
+	      "      The utilities ar, cpio, file and m4 are required. \n" \
+	      "" >> $(WARNING_FILE) ; \
+	  fi; \
+	done
+endif
 endif
 
 ######################################################
@@ -999,7 +1009,8 @@
 	    "      This is normally obtained from the WINDOWSSDKDIR." \
 	    "" >> $(ERROR_FILE)
   endif
-  ifeq ($(wildcard $(DUMPBIN)),)
+  # MinGW/MSYS make 3.81 will not tolerate a path with a quoted substring
+  ifeq ($(wildcard $(subst ",,$(DUMPBIN))),)
 	@$(ECHO) "ERROR: Cannot find the DUMPBIN utility from path: $(DUMPBIN)\n" \
 	    "      This is normally obtained from the COMPILER_PATH." \
 	    "" >> $(ERROR_FILE)
--- a/make/java/java/Exportedfiles.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/java/Exportedfiles.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 1997, 2006, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 1997, 2012, 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
@@ -66,6 +66,7 @@
     java/util/prefs/FileSystemPreferences.java \
     java/io/Console.java \
     java/io/FileDescriptor.java \
+    java/io/DefaultFileSystem.java \
     java/io/InputStream.java \
     java/io/FileInputStream.java \
     java/io/FileOutputStream.java \
@@ -142,6 +143,7 @@
     java/io/Console.java \
     java/io/FileSystem.java \
     java/io/FileDescriptor.java \
+    java/io/DefaultFileSystem.java \
     java/io/InputStream.java \
     java/io/FileInputStream.java \
     java/io/FileOutputStream.java \
--- a/make/java/java/FILES_c.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/java/FILES_c.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 1996, 2006, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 1996, 2012, 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
@@ -32,7 +32,6 @@
 	Compiler.c \
 	Console_md.c \
 	Double.c \
-	FileSystem_md.c \
 	FileDescriptor_md.c \
 	FileInputStream.c \
 	FileInputStream_md.c \
--- a/make/java/java/FILES_java.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/java/FILES_java.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 1996, 2011, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 1996, 2012, 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
@@ -438,6 +438,7 @@
     java/io/File.java \
     java/io/FileSystem.java \
     java/io/FileDescriptor.java \
+    java/io/DefaultFileSystem.java \
     java/io/FilenameFilter.java \
     java/io/FileFilter.java \
     java/io/FilePermission.java \
--- a/make/java/java/genlocales.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/java/genlocales.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -38,31 +38,31 @@
 # only FILES_java and FILES_compiled_properties variables will be picked up
 #
 # $(BUILDDIR)/java/util/FILES_java.gmk & $(BUILDDIR)/java/util/FILES_properties.gmk
-# contain "sun.util.resources" for European language support
+# contain "sun.util.resources" for US language support
 
 include $(BUILDDIR)/java/util/FILES_java.gmk
 include $(BUILDDIR)/java/util/FILES_properties.gmk
 
-Euro_Resources_java := $(FILES_java)
-Euro_Resources_properties := $(FILES_compiled_properties)
+US_Resources_java := $(FILES_java)
+US_Resources_properties := $(FILES_compiled_properties)
 
 # $(BUILDDIR)/java/text/FILES_java.gmk contains the "sun.text.resources" for 
-# European language support
+# US language support
 
 include $(BUILDDIR)/java/text/base/FILES_java.gmk
 
-Euro_Resources_java += $(FILES_java)
+US_Resources_java += $(FILES_java)
 
 FILES_compiled_properties=
 
 # $(BUILDDIR)/sun/text/FILES_java.gmk & $(BUILDDIR)/sun/text/FILES_properties.gmk
-# contain both resources for Non-European language support
+# contain both resources for Non-US language support
 
 include $(BUILDDIR)/sun/text/FILES_java.gmk
 include $(BUILDDIR)/sun/text/FILES_properties.gmk
 
-NonEuro_Resources_java := $(FILES_java)
-NonEuro_Resources_properties := $(FILES_compiled_properties)
+NonUS_Resources_java := $(FILES_java)
+NonUS_Resources_properties := $(FILES_compiled_properties)
 
 # Restore the orignal FILES_java & FILES_compiled_properties variables
 FILES_java := $(FILES_java_orig)
@@ -80,30 +80,30 @@
 ifeq ($(PLATFORM), macosx)
 
 $(LocaleDataMetaInfo_Dest):$(LocaleDataMetaInfo_Src) $(LOCALEGEN_SH)
-	@$(RM) $@.tmp.euro $@.tmp.noneuro;
+	@$(RM) $@.tmp.us $@.tmp.nonus;
 	@$(prep-target) 
-	@$(ECHO) $(Euro_Resources_properties) | $(NAWK) 'gsub(/.properties/,"\n") {print}'  > $@.tmp.euro;
-	@$(ECHO) $(Euro_Resources_java) | $(NAWK) 'gsub(/.java/,"\n") {print}' >> $@.tmp.euro;
-	@$(ECHO) $(NonEuro_Resources_properties) | $(NAWK) 'gsub(/.properties/,"\n") {print}' > $@.tmp.noneuro;
-	@$(ECHO) $(NonEuro_Resources_java) | $(NAWK) 'gsub(/.java/,"\n") {print}' >> $@.tmp.noneuro;
+	@$(ECHO) $(US_Resources_properties) | $(NAWK) 'gsub(/.properties/,"\n") {print}'  > $@.tmp.us;
+	@$(ECHO) $(US_Resources_java) | $(NAWK) 'gsub(/.java/,"\n") {print}' >> $@.tmp.us;
+	@$(ECHO) $(NonUS_Resources_properties) | $(NAWK) 'gsub(/.properties/,"\n") {print}' > $@.tmp.nonus;
+	@$(ECHO) $(NonUS_Resources_java) | $(NAWK) 'gsub(/.java/,"\n") {print}' >> $@.tmp.nonus;
 	NAWK="$(NAWK)" SED="$(SED)" SORT="$(SORT)" \
-	     $(SH) $(LOCALEGEN_SH) $(RESOURCE_NAMES) $@.tmp.euro \
-		$@.tmp.noneuro $< $@
-	@$(RM) $@.tmp.euro $@.tmp.noneuro;
+	     $(SH) $(LOCALEGEN_SH) $(RESOURCE_NAMES) $@.tmp.us \
+		$@.tmp.nonus $< $@
+	@$(RM) $@.tmp.us $@.tmp.nonus;
 
 else
 
 $(LocaleDataMetaInfo_Dest):$(LocaleDataMetaInfo_Src) $(LOCALEGEN_SH)
-	@$(RM) $@.tmp.euro $@.tmp.noneuro;
+	@$(RM) $@.tmp.us $@.tmp.nonus;
 	@$(prep-target) 
-	@$(ECHO) $(subst .properties,'\n',$(Euro_Resources_properties)) > $@.tmp.euro;
-	@$(ECHO) $(subst .java,'\n',$(Euro_Resources_java)) >> $@.tmp.euro;	
-	@$(ECHO) $(subst .properties,'\n',$(NonEuro_Resources_properties)) > $@.tmp.noneuro;
-	@$(ECHO) $(subst .java,'\n',$(NonEuro_Resources_java)) >> $@.tmp.noneuro;
+	@$(ECHO) $(subst .properties,'\n',$(US_Resources_properties)) > $@.tmp.us;
+	@$(ECHO) $(subst .java,'\n',$(US_Resources_java)) >> $@.tmp.us;	
+	@$(ECHO) $(subst .properties,'\n',$(NonUS_Resources_properties)) > $@.tmp.nonus;
+	@$(ECHO) $(subst .java,'\n',$(NonUS_Resources_java)) >> $@.tmp.nonus;
 	NAWK="$(NAWK)" SED="$(SED)" SORT="$(SORT)" \
-	     $(SH) $(LOCALEGEN_SH) $(RESOURCE_NAMES) $@.tmp.euro \
-		$@.tmp.noneuro $< $@
-	@$(RM) $@.tmp.euro $@.tmp.noneuro;
+	     $(SH) $(LOCALEGEN_SH) $(RESOURCE_NAMES) $@.tmp.us \
+		$@.tmp.nonus $< $@
+	@$(RM) $@.tmp.us $@.tmp.nonus;
 endif
 	
 genlocales : $(LocaleDataMetaInfo_Dest)  
--- a/make/java/java/localegen.sh	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/java/localegen.sh	Mon Nov 05 10:33:18 2012 -0500
@@ -35,11 +35,11 @@
 # A list of resource base name list;
 RESOURCE_NAMES=$1
 
-# A list of European resources;
-EURO_FILES_LIST=$2
+# A list of US resources;
+US_FILES_LIST=$2
 
-# A list of non-European resources;
-NONEURO_FILES_LIST=$3
+# A list of non-US resources;
+NONUS_FILES_LIST=$3
 
 INPUT_FILE=$4
 OUTPUT_FILE=$5
@@ -53,23 +53,23 @@
 sed_script="$SED -e \"s@^#warn .*@// -- This file was mechanically generated: Do not edit! -- //@\" "
 
 # ja-JP-JP and th-TH-TH need to be manually added, as they don't have any resource files.
-noneuroall=" ja-JP-JP th-TH-TH "
+nonusall=" ja-JP-JP th-TH-TH "
 
 for FILE in $RESOURCE_NAMES
 do
-    getlocalelist $FILE $EURO_FILES_LIST
-    sed_script=$sed_script"-e \"s@#"$FILE"_EuroLocales#@$localelist@g\" "
-    euroall=$euroall" "$localelist
-    getlocalelist $FILE $NONEURO_FILES_LIST
-    sed_script=$sed_script"-e \"s@#"$FILE"_NonEuroLocales#@$localelist@g\" "
-    noneuroall=$noneuroall" "$localelist
+    getlocalelist $FILE $US_FILES_LIST
+    sed_script=$sed_script"-e \"s@#"$FILE"_USLocales#@$localelist@g\" "
+    usall=$usall" "$localelist
+    getlocalelist $FILE $NONUS_FILES_LIST
+    sed_script=$sed_script"-e \"s@#"$FILE"_NonUSLocales#@$localelist@g\" "
+    nonusall=$nonusall" "$localelist
 done
 
-euroall=`(for LOC in $euroall; do echo $LOC;done) |$SORT -u`
-noneuroall=`(for LOC in $noneuroall; do echo $LOC;done) |$SORT -u`
+usall=`(for LOC in $usall; do echo $LOC;done) |$SORT -u`
+nonusall=`(for LOC in $nonusall; do echo $LOC;done) |$SORT -u`
 
-sed_script=$sed_script"-e \"s@#AvailableLocales_EuroLocales#@$euroall@g\" "
-sed_script=$sed_script"-e \"s@#AvailableLocales_NonEuroLocales#@$noneuroall@g\" "
+sed_script=$sed_script"-e \"s@#AvailableLocales_USLocales#@$usall@g\" "
+sed_script=$sed_script"-e \"s@#AvailableLocales_NonUSLocales#@$nonusall@g\" "
 
 sed_script=$sed_script"$INPUT_FILE > $OUTPUT_FILE"
 eval $sed_script
--- a/make/java/java/mapfile-vers	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/java/mapfile-vers	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 1997, 2009, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 1997, 2012, 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
@@ -87,7 +87,6 @@
 		Java_java_io_FileOutputStream_open;
 		Java_java_io_FileOutputStream_write;
 		Java_java_io_FileOutputStream_writeBytes;
-		Java_java_io_FileSystem_getFileSystem;
 		Java_java_io_ObjectInputStream_bytesToDoubles;
 		Java_java_io_ObjectInputStream_bytesToFloats;
 		Java_java_io_ObjectOutputStream_doublesToBytes;
--- a/make/java/text/base/FILES_java.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/text/base/FILES_java.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -103,150 +103,7 @@
         sun/text/resources/BreakIteratorInfo.java \
 	\
         sun/text/resources/CollationData.java \
-        sun/text/resources/be/CollationData_be.java \
-        sun/text/resources/bg/CollationData_bg.java \
-        sun/text/resources/ca/CollationData_ca.java \
-        sun/text/resources/cs/CollationData_cs.java \
-        sun/text/resources/da/CollationData_da.java \
-        sun/text/resources/el/CollationData_el.java \
-        sun/text/resources/es/CollationData_es.java \
-        sun/text/resources/et/CollationData_et.java \
-        sun/text/resources/fi/CollationData_fi.java \
-        sun/text/resources/fr/CollationData_fr.java \
-        sun/text/resources/hr/CollationData_hr.java \
-        sun/text/resources/hu/CollationData_hu.java \
-        sun/text/resources/is/CollationData_is.java \
-        sun/text/resources/lt/CollationData_lt.java \
-        sun/text/resources/lv/CollationData_lv.java \
-        sun/text/resources/mk/CollationData_mk.java \
-        sun/text/resources/no/CollationData_no.java \
-        sun/text/resources/pl/CollationData_pl.java \
-        sun/text/resources/ro/CollationData_ro.java \
-        sun/text/resources/ru/CollationData_ru.java \
-        sun/text/resources/sk/CollationData_sk.java \
-        sun/text/resources/sl/CollationData_sl.java \
-        sun/text/resources/sq/CollationData_sq.java \
-        sun/text/resources/sr/CollationData_sr.java \
-        sun/text/resources/sr/CollationData_sr_Latn.java \
-        sun/text/resources/sv/CollationData_sv.java \
-        sun/text/resources/tr/CollationData_tr.java \
-        sun/text/resources/uk/CollationData_uk.java \
 	\
         sun/text/resources/FormatData.java \
-        sun/text/resources/be/FormatData_be.java \
-        sun/text/resources/be/FormatData_be_BY.java \
-        sun/text/resources/bg/FormatData_bg.java \
-        sun/text/resources/bg/FormatData_bg_BG.java \
-        sun/text/resources/ca/FormatData_ca.java \
-        sun/text/resources/ca/FormatData_ca_ES.java \
-        sun/text/resources/cs/FormatData_cs.java \
-        sun/text/resources/cs/FormatData_cs_CZ.java \
-        sun/text/resources/da/FormatData_da.java \
-        sun/text/resources/da/FormatData_da_DK.java \
-        sun/text/resources/de/FormatData_de.java \
-        sun/text/resources/de/FormatData_de_AT.java \
-        sun/text/resources/de/FormatData_de_CH.java \
-        sun/text/resources/de/FormatData_de_DE.java \
-        sun/text/resources/de/FormatData_de_LU.java \
-        sun/text/resources/el/FormatData_el.java \
-        sun/text/resources/el/FormatData_el_CY.java \
-        sun/text/resources/el/FormatData_el_GR.java \
         sun/text/resources/en/FormatData_en.java \
-        sun/text/resources/en/FormatData_en_US.java \
-        sun/text/resources/en/FormatData_en_AU.java \
-        sun/text/resources/en/FormatData_en_CA.java \
-        sun/text/resources/en/FormatData_en_GB.java \
-        sun/text/resources/en/FormatData_en_IE.java \
-        sun/text/resources/en/FormatData_en_IN.java \
-        sun/text/resources/en/FormatData_en_MT.java \
-        sun/text/resources/en/FormatData_en_NZ.java \
-        sun/text/resources/en/FormatData_en_PH.java \
-        sun/text/resources/en/FormatData_en_SG.java \
-        sun/text/resources/en/FormatData_en_ZA.java \
-        sun/text/resources/es/FormatData_es.java \
-        sun/text/resources/es/FormatData_es_BO.java \
-        sun/text/resources/es/FormatData_es_AR.java \
-        sun/text/resources/es/FormatData_es_CL.java \
-        sun/text/resources/es/FormatData_es_CO.java \
-        sun/text/resources/es/FormatData_es_CR.java \
-        sun/text/resources/es/FormatData_es_DO.java \
-        sun/text/resources/es/FormatData_es_EC.java \
-        sun/text/resources/es/FormatData_es_ES.java \
-        sun/text/resources/es/FormatData_es_GT.java \
-        sun/text/resources/es/FormatData_es_HN.java \
-        sun/text/resources/es/FormatData_es_MX.java \
-        sun/text/resources/es/FormatData_es_NI.java \
-        sun/text/resources/es/FormatData_es_PA.java \
-        sun/text/resources/es/FormatData_es_PE.java \
-        sun/text/resources/es/FormatData_es_PR.java \
-        sun/text/resources/es/FormatData_es_PY.java \
-        sun/text/resources/es/FormatData_es_SV.java \
-        sun/text/resources/es/FormatData_es_US.java \
-        sun/text/resources/es/FormatData_es_UY.java \
-        sun/text/resources/es/FormatData_es_VE.java \
-        sun/text/resources/et/FormatData_et.java \
-        sun/text/resources/et/FormatData_et_EE.java \
-        sun/text/resources/fi/FormatData_fi.java \
-        sun/text/resources/fi/FormatData_fi_FI.java \
-        sun/text/resources/fr/FormatData_fr.java \
-        sun/text/resources/fr/FormatData_fr_BE.java \
-        sun/text/resources/fr/FormatData_fr_CA.java \
-        sun/text/resources/fr/FormatData_fr_CH.java \
-        sun/text/resources/fr/FormatData_fr_FR.java \
-        sun/text/resources/ga/FormatData_ga.java \
-        sun/text/resources/ga/FormatData_ga_IE.java \
-        sun/text/resources/hr/FormatData_hr.java \
-        sun/text/resources/hr/FormatData_hr_HR.java \
-        sun/text/resources/hu/FormatData_hu.java \
-        sun/text/resources/hu/FormatData_hu_HU.java \
-        sun/text/resources/in/FormatData_in.java \
-        sun/text/resources/in/FormatData_in_ID.java \
-        sun/text/resources/is/FormatData_is.java \
-        sun/text/resources/is/FormatData_is_IS.java \
-        sun/text/resources/it/FormatData_it.java \
-        sun/text/resources/it/FormatData_it_CH.java \
-        sun/text/resources/it/FormatData_it_IT.java \
-        sun/text/resources/lt/FormatData_lt.java \
-        sun/text/resources/lt/FormatData_lt_LT.java \
-        sun/text/resources/lv/FormatData_lv.java \
-        sun/text/resources/lv/FormatData_lv_LV.java \
-        sun/text/resources/mk/FormatData_mk.java \
-        sun/text/resources/mk/FormatData_mk_MK.java \
-        sun/text/resources/ms/FormatData_ms.java \
-        sun/text/resources/ms/FormatData_ms_MY.java \
-        sun/text/resources/mt/FormatData_mt.java \
-        sun/text/resources/mt/FormatData_mt_MT.java \
-        sun/text/resources/nl/FormatData_nl.java \
-        sun/text/resources/nl/FormatData_nl_BE.java \
-        sun/text/resources/nl/FormatData_nl_NL.java \
-        sun/text/resources/no/FormatData_no.java \
-        sun/text/resources/no/FormatData_no_NO.java \
-        sun/text/resources/no/FormatData_no_NO_NY.java \
-        sun/text/resources/pl/FormatData_pl.java \
-        sun/text/resources/pl/FormatData_pl_PL.java \
-        sun/text/resources/pt/FormatData_pt.java \
-        sun/text/resources/pt/FormatData_pt_BR.java \
-        sun/text/resources/pt/FormatData_pt_PT.java \
-        sun/text/resources/ro/FormatData_ro.java \
-        sun/text/resources/ro/FormatData_ro_RO.java \
-        sun/text/resources/ru/FormatData_ru.java \
-        sun/text/resources/ru/FormatData_ru_RU.java \
-        sun/text/resources/sk/FormatData_sk.java \
-        sun/text/resources/sk/FormatData_sk_SK.java \
-        sun/text/resources/sl/FormatData_sl.java \
-        sun/text/resources/sl/FormatData_sl_SI.java \
-        sun/text/resources/sq/FormatData_sq.java \
-        sun/text/resources/sq/FormatData_sq_AL.java \
-        sun/text/resources/sr/FormatData_sr.java \
-        sun/text/resources/sr/FormatData_sr_BA.java \
-        sun/text/resources/sr/FormatData_sr_CS.java \
-        sun/text/resources/sr/FormatData_sr_ME.java \
-        sun/text/resources/sr/FormatData_sr_RS.java \
-        sun/text/resources/sr/FormatData_sr_Latn.java \
-        sun/text/resources/sr/FormatData_sr_Latn_ME.java \
-        sun/text/resources/sv/FormatData_sv.java \
-        sun/text/resources/sv/FormatData_sv_SE.java \
-        sun/text/resources/tr/FormatData_tr.java \
-        sun/text/resources/tr/FormatData_tr_TR.java \
-        sun/text/resources/uk/FormatData_uk.java \
-        sun/text/resources/uk/FormatData_uk_UA.java
+        sun/text/resources/en/FormatData_en_US.java
--- a/make/java/util/FILES_java.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/util/FILES_java.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -29,13 +29,4 @@
         sun/util/resources/LocaleNamesBundle.java \
         sun/util/resources/TimeZoneNamesBundle.java \
         sun/util/resources/TimeZoneNames.java \
-        sun/util/resources/de/TimeZoneNames_de.java \
-        sun/util/resources/en/TimeZoneNames_en.java \
-        sun/util/resources/en/TimeZoneNames_en_CA.java \
-        sun/util/resources/en/TimeZoneNames_en_GB.java \
-        sun/util/resources/en/TimeZoneNames_en_IE.java \
-        sun/util/resources/es/TimeZoneNames_es.java \
-        sun/util/resources/fr/TimeZoneNames_fr.java \
-        sun/util/resources/it/TimeZoneNames_it.java \
-        sun/util/resources/pt/TimeZoneNames_pt_BR.java \
-        sun/util/resources/sv/TimeZoneNames_sv.java
+        sun/util/resources/en/TimeZoneNames_en.java
--- a/make/java/util/FILES_properties.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/java/util/FILES_properties.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -25,189 +25,10 @@
 
 FILES_compiled_properties = \
         sun/util/resources/LocaleNames.properties \
-        sun/util/resources/be/LocaleNames_be.properties \
-        sun/util/resources/bg/LocaleNames_bg.properties \
-        sun/util/resources/ca/LocaleNames_ca.properties \
-        sun/util/resources/cs/LocaleNames_cs.properties \
-        sun/util/resources/da/LocaleNames_da.properties \
-        sun/util/resources/de/LocaleNames_de.properties \
-        sun/util/resources/el/LocaleNames_el.properties \
-        sun/util/resources/el/LocaleNames_el_CY.properties \
         sun/util/resources/en/LocaleNames_en.properties \
-        sun/util/resources/en/LocaleNames_en_MT.properties \
-        sun/util/resources/en/LocaleNames_en_PH.properties \
-        sun/util/resources/en/LocaleNames_en_SG.properties \
-        sun/util/resources/es/LocaleNames_es.properties \
-        sun/util/resources/es/LocaleNames_es_US.properties \
-        sun/util/resources/et/LocaleNames_et.properties \
-        sun/util/resources/fi/LocaleNames_fi.properties \
-        sun/util/resources/fr/LocaleNames_fr.properties \
-        sun/util/resources/ga/LocaleNames_ga.properties \
-        sun/util/resources/hr/LocaleNames_hr.properties \
-        sun/util/resources/hu/LocaleNames_hu.properties \
-        sun/util/resources/in/LocaleNames_in.properties \
-        sun/util/resources/is/LocaleNames_is.properties \
-        sun/util/resources/it/LocaleNames_it.properties \
-        sun/util/resources/lt/LocaleNames_lt.properties \
-        sun/util/resources/lv/LocaleNames_lv.properties \
-        sun/util/resources/mk/LocaleNames_mk.properties \
-        sun/util/resources/ms/LocaleNames_ms.properties \
-        sun/util/resources/mt/LocaleNames_mt.properties \
-        sun/util/resources/nl/LocaleNames_nl.properties \
-        sun/util/resources/no/LocaleNames_no.properties \
-        sun/util/resources/no/LocaleNames_no_NO_NY.properties \
-        sun/util/resources/pl/LocaleNames_pl.properties \
-        sun/util/resources/pt/LocaleNames_pt.properties \
-        sun/util/resources/pt/LocaleNames_pt_BR.properties \
-        sun/util/resources/pt/LocaleNames_pt_PT.properties \
-        sun/util/resources/ro/LocaleNames_ro.properties \
-        sun/util/resources/ru/LocaleNames_ru.properties \
-        sun/util/resources/sk/LocaleNames_sk.properties \
-        sun/util/resources/sl/LocaleNames_sl.properties \
-        sun/util/resources/sq/LocaleNames_sq.properties \
-        sun/util/resources/sr/LocaleNames_sr.properties \
-        sun/util/resources/sr/LocaleNames_sr_Latn.properties \
-        sun/util/resources/sv/LocaleNames_sv.properties \
-        sun/util/resources/tr/LocaleNames_tr.properties \
-        sun/util/resources/uk/LocaleNames_uk.properties \
 	\
         sun/util/resources/CalendarData.properties \
-        sun/util/resources/be/CalendarData_be.properties \
-        sun/util/resources/bg/CalendarData_bg.properties \
-        sun/util/resources/ca/CalendarData_ca.properties \
-        sun/util/resources/cs/CalendarData_cs.properties \
-        sun/util/resources/da/CalendarData_da.properties \
-        sun/util/resources/de/CalendarData_de.properties \
-        sun/util/resources/el/CalendarData_el.properties \
-        sun/util/resources/el/CalendarData_el_CY.properties \
         sun/util/resources/en/CalendarData_en.properties \
-        sun/util/resources/en/CalendarData_en_GB.properties \
-        sun/util/resources/en/CalendarData_en_IE.properties \
-        sun/util/resources/en/CalendarData_en_MT.properties \
-        sun/util/resources/es/CalendarData_es.properties \
-        sun/util/resources/es/CalendarData_es_ES.properties \
-        sun/util/resources/es/CalendarData_es_US.properties \
-        sun/util/resources/et/CalendarData_et.properties \
-        sun/util/resources/fi/CalendarData_fi.properties \
-        sun/util/resources/fr/CalendarData_fr.properties \
-        sun/util/resources/fr/CalendarData_fr_CA.properties \
-        sun/util/resources/hr/CalendarData_hr.properties \
-        sun/util/resources/hu/CalendarData_hu.properties \
-        sun/util/resources/in/CalendarData_in_ID.properties \
-        sun/util/resources/is/CalendarData_is.properties \
-        sun/util/resources/it/CalendarData_it.properties \
-        sun/util/resources/lt/CalendarData_lt.properties \
-        sun/util/resources/lv/CalendarData_lv.properties \
-        sun/util/resources/mk/CalendarData_mk.properties \
-        sun/util/resources/ms/CalendarData_ms_MY.properties \
-        sun/util/resources/mt/CalendarData_mt.properties \
-        sun/util/resources/mt/CalendarData_mt_MT.properties \
-        sun/util/resources/nl/CalendarData_nl.properties \
-        sun/util/resources/no/CalendarData_no.properties \
-        sun/util/resources/pl/CalendarData_pl.properties \
-        sun/util/resources/pt/CalendarData_pt.properties \
-        sun/util/resources/pt/CalendarData_pt_PT.properties \
-        sun/util/resources/ro/CalendarData_ro.properties \
-        sun/util/resources/ru/CalendarData_ru.properties \
-        sun/util/resources/sk/CalendarData_sk.properties \
-        sun/util/resources/sl/CalendarData_sl.properties \
-        sun/util/resources/sq/CalendarData_sq.properties \
-        sun/util/resources/sr/CalendarData_sr.properties \
-        sun/util/resources/sr/CalendarData_sr_Latn_BA.properties \
-        sun/util/resources/sr/CalendarData_sr_Latn_ME.properties \
-        sun/util/resources/sr/CalendarData_sr_Latn_RS.properties \
-        sun/util/resources/sv/CalendarData_sv.properties \
-        sun/util/resources/tr/CalendarData_tr.properties \
-        sun/util/resources/uk/CalendarData_uk.properties \
 	\
         sun/util/resources/CurrencyNames.properties \
-        sun/util/resources/be/CurrencyNames_be_BY.properties \
-        sun/util/resources/bg/CurrencyNames_bg_BG.properties \
-        sun/util/resources/ca/CurrencyNames_ca_ES.properties \
-        sun/util/resources/cs/CurrencyNames_cs_CZ.properties \
-        sun/util/resources/da/CurrencyNames_da_DK.properties \
-        sun/util/resources/de/CurrencyNames_de.properties \
-        sun/util/resources/de/CurrencyNames_de_AT.properties \
-        sun/util/resources/de/CurrencyNames_de_CH.properties \
-        sun/util/resources/de/CurrencyNames_de_DE.properties \
-        sun/util/resources/de/CurrencyNames_de_GR.properties \
-        sun/util/resources/de/CurrencyNames_de_LU.properties \
-        sun/util/resources/el/CurrencyNames_el_CY.properties \
-        sun/util/resources/el/CurrencyNames_el_GR.properties \
-        sun/util/resources/en/CurrencyNames_en_AU.properties \
-        sun/util/resources/en/CurrencyNames_en_CA.properties \
-        sun/util/resources/en/CurrencyNames_en_GB.properties \
-        sun/util/resources/en/CurrencyNames_en_IE.properties \
-        sun/util/resources/en/CurrencyNames_en_IN.properties \
-        sun/util/resources/en/CurrencyNames_en_MT.properties \
-        sun/util/resources/en/CurrencyNames_en_NZ.properties \
-        sun/util/resources/en/CurrencyNames_en_PH.properties \
-        sun/util/resources/en/CurrencyNames_en_SG.properties \
-        sun/util/resources/en/CurrencyNames_en_US.properties \
-        sun/util/resources/en/CurrencyNames_en_ZA.properties \
-        sun/util/resources/es/CurrencyNames_es.properties \
-        sun/util/resources/es/CurrencyNames_es_AR.properties \
-        sun/util/resources/es/CurrencyNames_es_BO.properties \
-        sun/util/resources/es/CurrencyNames_es_CL.properties \
-        sun/util/resources/es/CurrencyNames_es_CO.properties \
-        sun/util/resources/es/CurrencyNames_es_CR.properties \
-        sun/util/resources/es/CurrencyNames_es_CU.properties \
-        sun/util/resources/es/CurrencyNames_es_DO.properties \
-        sun/util/resources/es/CurrencyNames_es_EC.properties \
-        sun/util/resources/es/CurrencyNames_es_ES.properties \
-        sun/util/resources/es/CurrencyNames_es_GT.properties \
-        sun/util/resources/es/CurrencyNames_es_HN.properties \
-        sun/util/resources/es/CurrencyNames_es_MX.properties \
-        sun/util/resources/es/CurrencyNames_es_NI.properties \
-        sun/util/resources/es/CurrencyNames_es_PA.properties \
-        sun/util/resources/es/CurrencyNames_es_PE.properties \
-        sun/util/resources/es/CurrencyNames_es_PR.properties \
-        sun/util/resources/es/CurrencyNames_es_PY.properties \
-        sun/util/resources/es/CurrencyNames_es_SV.properties \
-        sun/util/resources/es/CurrencyNames_es_US.properties \
-        sun/util/resources/es/CurrencyNames_es_UY.properties \
-        sun/util/resources/es/CurrencyNames_es_VE.properties \
-        sun/util/resources/et/CurrencyNames_et_EE.properties \
-        sun/util/resources/fi/CurrencyNames_fi_FI.properties \
-        sun/util/resources/fr/CurrencyNames_fr.properties \
-        sun/util/resources/fr/CurrencyNames_fr_BE.properties \
-        sun/util/resources/fr/CurrencyNames_fr_CA.properties \
-        sun/util/resources/fr/CurrencyNames_fr_CH.properties \
-        sun/util/resources/fr/CurrencyNames_fr_FR.properties \
-        sun/util/resources/fr/CurrencyNames_fr_LU.properties \
-        sun/util/resources/ga/CurrencyNames_ga_IE.properties \
-        sun/util/resources/hr/CurrencyNames_hr_HR.properties \
-        sun/util/resources/hu/CurrencyNames_hu_HU.properties \
-        sun/util/resources/in/CurrencyNames_in_ID.properties \
-        sun/util/resources/is/CurrencyNames_is_IS.properties \
-        sun/util/resources/it/CurrencyNames_it.properties \
-        sun/util/resources/it/CurrencyNames_it_CH.properties \
-        sun/util/resources/it/CurrencyNames_it_IT.properties \
-        sun/util/resources/lt/CurrencyNames_lt_LT.properties \
-        sun/util/resources/lv/CurrencyNames_lv_LV.properties \
-        sun/util/resources/mk/CurrencyNames_mk_MK.properties \
-        sun/util/resources/ms/CurrencyNames_ms_MY.properties \
-        sun/util/resources/mt/CurrencyNames_mt_MT.properties \
-        sun/util/resources/nl/CurrencyNames_nl_BE.properties \
-        sun/util/resources/nl/CurrencyNames_nl_NL.properties \
-        sun/util/resources/no/CurrencyNames_no_NO.properties \
-        sun/util/resources/pl/CurrencyNames_pl_PL.properties \
-        sun/util/resources/pt/CurrencyNames_pt.properties \
-        sun/util/resources/pt/CurrencyNames_pt_BR.properties \
-        sun/util/resources/pt/CurrencyNames_pt_PT.properties \
-        sun/util/resources/ro/CurrencyNames_ro_RO.properties \
-        sun/util/resources/ru/CurrencyNames_ru_RU.properties \
-        sun/util/resources/sk/CurrencyNames_sk_SK.properties \
-        sun/util/resources/sl/CurrencyNames_sl_SI.properties \
-        sun/util/resources/sq/CurrencyNames_sq_AL.properties \
-        sun/util/resources/sr/CurrencyNames_sr_BA.properties \
-        sun/util/resources/sr/CurrencyNames_sr_CS.properties \
-        sun/util/resources/sr/CurrencyNames_sr_ME.properties \
-        sun/util/resources/sr/CurrencyNames_sr_RS.properties \
-        sun/util/resources/sr/CurrencyNames_sr_Latn_BA.properties \
-        sun/util/resources/sr/CurrencyNames_sr_Latn_ME.properties \
-        sun/util/resources/sr/CurrencyNames_sr_Latn_RS.properties \
-        sun/util/resources/sv/CurrencyNames_sv.properties \
-        sun/util/resources/sv/CurrencyNames_sv_SE.properties \
-        sun/util/resources/tr/CurrencyNames_tr_TR.properties \
-        sun/util/resources/uk/CurrencyNames_uk_UA.properties
+        sun/util/resources/en/CurrencyNames_en_US.properties
--- a/make/javax/crypto/Defs-jce.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/javax/crypto/Defs-jce.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 2007, 2011, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2007, 2012, 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
@@ -31,7 +31,7 @@
 JCE_MANIFEST_FILE    = $(TEMPDIR)/manifest.mf
 $(JCE_MANIFEST_FILE): $(MAINMANIFEST)
 	$(prep-target)
-	$(SED) -e "s#@@RELEASE@@#$(RELEASE)#"           \
+	$(SED) -e "s#@@RELEASE@@#$(JDK_VERSION)#"       \
                -e "s#@@COMPANY_NAME@@#$(COMPANY_NAME)#" \
                $(MAINMANIFEST) >> $@
 	$(ECHO) "Extension-Name: javax.crypto" >> $@
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/jdk/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,38 @@
+#
+# Copyright (c) 1997, 2012, 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.
+#
+
+#
+# Makefile for building all of java
+#
+
+BUILDDIR = ..
+PRODUCT = jdk
+include $(BUILDDIR)/common/Defs.gmk
+
+SUBDIRS = asm
+include $(BUILDDIR)/common/Subdirs.gmk
+
+all build clean clobber::
+	$(SUBDIRS-loop)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/jdk/asm/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+#
+# Copyright (c) 1995, 2012, 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.
+#
+
+BUILDDIR = ../..
+PACKAGE = jdk.internal.org.objectweb.asm
+PRODUCT = jdk
+JAVAC_LINT_OPTIONS=-Xlint:all
+include $(BUILDDIR)/common/Defs.gmk
+
+#
+# Files to compile
+#
+AUTO_FILES_JAVA_DIRS = jdk/internal/org/objectweb/asm
+
+#
+# Rules
+#
+include $(BUILDDIR)/common/Classes.gmk
--- a/make/jdk_generic_profile.sh	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/jdk_generic_profile.sh	Mon Nov 05 10:33:18 2012 -0500
@@ -176,17 +176,38 @@
   else
     windows_arch=i586
   fi
+
+  repo=`hg root | sed -e 's@\\\\@/@g'`
   # We need to check if we are running a CYGWIN shell
-  if [ "$(uname -a | fgrep Cygwin)" != "" -a -f /bin/cygpath ] ; then
+  if [ "$(echo ${osname} | fgrep Cygwin)" != "" -a -f /bin/cygpath ] ; then
     # For CYGWIN, uname will have "Cygwin" in it, and /bin/cygpath should exist
     # Utility to convert to short pathnames without spaces
     cygpath="/usr/bin/cygpath -a -m -s"
+    cygpathp="/usr/bin/cygpath -p"
     # Most unix utilities are in the /usr/bin
     unixcommand_path="/usr/bin"
     # Make the prompt tell you CYGWIN
     export PS1="CYGWIN:${COMPUTERNAME}:${USERNAME}[\!] "
+  elif [ "$(echo ${osname} | fgrep MINGW)" != "" ] ; then
+    # Utility to convert to short pathnames without spaces
+    cygpath="${repo}/make/tools/msys_build_scripts/dospath.sh"
+    if [ ! -f ${cygpath} ] ; then
+        echo "ERROR: Cannot find cygpath or equivalent on this machine"
+        exit 1
+    fi
+    # Utility to fix a path to MinGW/MSYS format - the equivalent of 'cygpath -p'
+    for tfile in "${repo}/make/scripts/fixpath.pl" "${repo}/../make/scripts/fixpath.pl"; do
+        if [ -f ${tfile} ] ; then
+            cygpathp="/bin/perl ${tfile} -m"
+        fi
+    done;
+    if [ -z "${cygpathp}" ] ; then
+        echo "ERROR: Cannot find make/scripts/fixpath.pl on this machine"
+        exit 1
+    fi
+    unixcommand_path="/usr/bin"
   else
-    echo "ERROR: Cannot find CYGWIN on this machine"
+    echo "ERROR: Cannot find CYGWIN or MinGW/MSYS on this machine"
     exit 1
   fi
   if [ "${ALT_UNIXCOMMAND_PATH}" != "" ] ; then
@@ -204,17 +225,18 @@
   else
     sys_root=$(${cygpath} "C:/WINNT")
   fi
-  path4sdk="${unixcommand_path};${sys_root}/system32;${sys_root};${sys_root}/System32/Wbem"
   if [ ! -d "${sys_root}" ] ; then
     echo "WARNING: No system root found at: ${sys_root}"
   fi
 
+  # Build a : separated path making sure each segment is acceptable to ${osname}
+  path4sdk="${unixcommand_path}:"`${cygpathp} "${sys_root}/system32;${sys_root};${sys_root}/System32/Wbem"`
+
   # Compiler setup (nasty part)
   #   NOTE: You can use vcvars32.bat to set PATH, LIB, and INCLUDE.
   #   NOTE: CYGWIN has a link.exe too, make sure the compilers are first
 
   # Use supplied vsvars.sh
-  repo=`hg root`
   if [ -f "${repo}/make/scripts/vsvars.sh" ] ; then
     eval `sh ${repo}/make/scripts/vsvars.sh -v10`
   elif [ -f "${repo}/../make/scripts/vsvars.sh" ] ; then
--- a/make/sun/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -63,12 +63,6 @@
   LWAWT_SUBDIR = lwawt
 endif
 
-ifndef OPENJDK
-ifneq ($(PLATFORM), macosx)
-  JDBC_SUBDIR = jdbc
-endif
-endif
-
 ifdef OPENJDK
   RENDER_SUBDIR = pisces
 else
@@ -89,7 +83,7 @@
                      $(LWAWT_PRE_SUBDIR) $(DISPLAY_LIBS) $(DGA_SUBDIR) $(LWAWT_SUBDIR) \
                      jawt font jpeg cmm $(DISPLAY_TOOLS)
 SUBDIRS_management = management
-SUBDIRS_misc       = $(ORG_SUBDIR) rmi $(JDBC_SUBDIR) tracing
+SUBDIRS_misc       = $(ORG_SUBDIR) rmi tracing
 SUBDIRS_tools      = native2ascii serialver tools jconsole
 
 ifndef OPENJDK
--- a/make/sun/jdbc/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,142 +0,0 @@
-#
-# Copyright (c) 1996, 2011, 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.
-#
-
-#
-# Makefile for JDBC-ODBC Bridge Driver 
-#
-# Note - the native library for the bridge may be linked with the 
-# shared library for the ODBC driver manager.  Or dummy libraries
-# may be used to just create libJdbcOdbc.so with a dependency on
-# libodbc.so and libodbcinst.so.
-#
-
-BUILDDIR = ../..
-PACKAGE = sun.jdbc.odbc
-LIBRARY = JdbcOdbc
-PRODUCT = sun
-include $(BUILDDIR)/common/Defs.gmk
-
-#
-# Files
-#
-
-AUTO_FILES_JAVA_DIRS = sun/jdbc/odbc
-
-FILES_c = \
-	JdbcOdbc.c
-
-FILES_export = \
-    sun/jdbc/odbc/JdbcOdbc.java 
-
-# Use fake libraries on Solaris and Linux just so the library we create has
-#   a dependency on these two library names. (which are not part of the jdk)
-ifneq ($(PLATFORM), windows)
-  # In jdk5 and jdk6, and on Solaris 32bit, we would have required that
-  #    these two libraries exist at: $(ALT_ODBCDIR)/ISLIodbc/2.11/lib
-  #    In jdk7, we just fake them out like we did on Linux in jdk5 and jdk6.
-  #
-  # If you wanted to use the real odbc libraries, change the value of
-  #    ODBC_LIBRARY_LOCATION, and delete the variable assignments below.
-  #
-  # Tell linker to ignore missing externals when building this shared library.
-  LDFLAGS_DEFS_OPTION = -Xlinker -z -Xlinker nodefs
-  # Define a place to create the fake libraries and their names.
-  ODBC_LIBRARY_LOCATION = $(TEMPDIR)
-  ODBC_FAKE_LIBRARIES = $(ODBC_LIBRARY_LOCATION)/libodbcinst.so $(ODBC_LIBRARY_LOCATION)/libodbc.so
-  # Make sure they get created early.
-  INIT += $(ODBC_FAKE_LIBRARIES)
-endif
-
-#
-# Rules
-#
-include $(BUILDDIR)/common/Library.gmk
-
-#
-# The UNIX define specifies conditional compilation for UNIX
-#
-ifeq ($(PLATFORM), windows)
-  LDLIBS += odbc32.lib odbccp32.lib
-else
-  CFLAGS += -DUNIX
-  LDFLAGS += -L$(ODBC_LIBRARY_LOCATION) -lodbcinst -lodbc
-endif
-
-#
-# The native code for the bridge uses conditional compilation to 
-# support Solaris, Win95 and Mac PPC. This is the path to the shared C files
-# (which unfortunately are in the same directory as shared Java files).
-#
-vpath %.c $(CLOSED_SHARE_SRC)/classes/sun/jdbc/odbc
-
-#
-# Rules to generate fake libraries
-#
-
-ifdef ODBC_FAKE_LIBRARIES
-$(TEMPDIR)/dummyodbc.c: 
-	@$(prep-target)
-	$(ECHO) "void dummyOdbc(void){}" >> $@
-$(TEMPDIR)/dummyodbc.o: $(TEMPDIR)/dummyodbc.c
-	@$(prep-target)
-	$(COMPILE.c) $(CC_OBJECT_OUTPUT_FLAG)$@ $(CFLAGS_GPROF) $<
-$(ODBC_FAKE_LIBRARIES): $(TEMPDIR)/dummyodbc.o
-	@$(prep-target)
-	$(CC) $(SHARED_LIBRARY_FLAG) $(LDFLAGS_COMMON) -o $@ $< $(EXTRA_LIBS)
-clean::
-	$(RM) -f $(ODBC_FAKE_LIBRARIES)
-	$(RM) -f $(TEMPDIR)/dummyodbc.c
-	$(RM) -f $(TEMPDIR)/dummyodbc.o
-endif
-
-#
-# Files that need to be copied
-#
-SERVICEDIR = $(CLASSBINDIR)/META-INF/services
-
-FILES_copy = \
-	$(SERVICEDIR)/java.sql.Driver
-
-
-FILES_mkdirs = \
-	$(CLASSBINDIR)/META-INF \
-	$(CLASSBINDIR)/META-INF/services
-
-FILES_copydirs = \
-	$(CLASSBINDIR) \
-	$(FILES_mkdirs)
-
-build: copy-files
-
-copy-files: $(FILES_copy)
-
-$(SERVICEDIR)/%: $(CLOSED_SHARE_SRC)/classes/sun/jdbc/odbc/META-INF/services/%
-	$(install-file)
-
-clean clobber::
-	$(RM) $(FILES_copy)
-
-.PHONY: copy-files
-
--- a/make/sun/net/FILES_java.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/net/FILES_java.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -128,8 +128,6 @@
 	sun/net/www/content/audio/x_wav.java \
 	sun/net/www/protocol/ftp/Handler.java \
 	sun/net/www/protocol/ftp/FtpURLConnection.java \
-	sun/net/www/protocol/gopher/GopherClient.java \
-	sun/net/www/protocol/gopher/Handler.java \
 	sun/net/www/protocol/mailto/Handler.java \
 	sun/net/www/protocol/mailto/MailToURLConnection.java \
 	sun/net/idn/Punycode.java \
--- a/make/sun/security/ec/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/security/ec/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -246,9 +246,9 @@
 #
 # Build sunec.jar.
 #
-$(UNSIGNED_DIR)/sunec.jar: build
+$(UNSIGNED_DIR)/sunec.jar: build $(JCE_MANIFEST_FILE)
 	$(prep-target)
-	$(BOOT_JAR_CMD) cf $@ $(JAR_DIRS) \
+	$(BOOT_JAR_CMD) cmf $(JCE_MANIFEST_FILE) $@ $(JAR_DIRS) \
 	    $(BOOT_JAR_JFLAGS)
 	@$(java-vm-cleanup)
 
--- a/make/sun/security/mscapi/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/security/mscapi/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -209,9 +209,9 @@
 #
 # Build sunmscapi.jar.
 #
-$(UNSIGNED_DIR)/sunmscapi.jar: build
+$(UNSIGNED_DIR)/sunmscapi.jar: build $(JCE_MANIFEST_FILE)
 	$(prep-target)
-	$(BOOT_JAR_CMD) cf $@ $(JAR_DIRS) \
+	$(BOOT_JAR_CMD) cmf $(JCE_MANIFEST_FILE) $@ $(JAR_DIRS) \
 	    $(BOOT_JAR_JFLAGS)
 	@$(java-vm-cleanup)
 
--- a/make/sun/security/pkcs11/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/security/pkcs11/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -225,9 +225,9 @@
 #
 # Build sunpkcs11.jar.
 #
-$(UNSIGNED_DIR)/sunpkcs11.jar: build
+$(UNSIGNED_DIR)/sunpkcs11.jar: build $(JCE_MANIFEST_FILE)
 	$(prep-target)
-	$(BOOT_JAR_CMD) cf $@ $(JAR_DIRS) \
+	$(BOOT_JAR_CMD) cmf $(JCE_MANIFEST_FILE) $@ $(JAR_DIRS) \
 	    $(BOOT_JAR_JFLAGS)
 	@$(java-vm-cleanup)
 
--- a/make/sun/text/FILES_java.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/text/FILES_java.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -24,10 +24,10 @@
 #
 
 # Locale data files for lib/ext/localedata.jar.
-# This includes resource bundles and data for non-European
+# This includes resource bundles and data for non-US
 # languages in sun.text.resources as well as sun.util.resources.
 #
-# Locale data for European languages is built from
+# Locale data for US languages is built from
 # - make/java/text for classes in sun.text.resources
 # - make/java/util for classes in sun.util.resources
 #
@@ -36,11 +36,39 @@
 		sun/text/resources/th/BreakIteratorInfo_th.java \
 		\
 		sun/text/resources/ar/CollationData_ar.java \
+                sun/text/resources/be/CollationData_be.java \
+                sun/text/resources/bg/CollationData_bg.java \
+                sun/text/resources/ca/CollationData_ca.java \
+                sun/text/resources/cs/CollationData_cs.java \
+                sun/text/resources/da/CollationData_da.java \
+                sun/text/resources/el/CollationData_el.java \
+                sun/text/resources/es/CollationData_es.java \
+                sun/text/resources/et/CollationData_et.java \
+                sun/text/resources/fi/CollationData_fi.java \
+                sun/text/resources/fr/CollationData_fr.java \
 		sun/text/resources/hi/CollationData_hi.java \
+                sun/text/resources/hr/CollationData_hr.java \
+                sun/text/resources/hu/CollationData_hu.java \
+                sun/text/resources/is/CollationData_is.java \
 		sun/text/resources/iw/CollationData_iw.java \
 		sun/text/resources/ja/CollationData_ja.java \
 		sun/text/resources/ko/CollationData_ko.java \
+                sun/text/resources/lt/CollationData_lt.java \
+                sun/text/resources/lv/CollationData_lv.java \
+                sun/text/resources/mk/CollationData_mk.java \
+                sun/text/resources/no/CollationData_no.java \
+                sun/text/resources/pl/CollationData_pl.java \
+                sun/text/resources/ro/CollationData_ro.java \
+                sun/text/resources/ru/CollationData_ru.java \
+                sun/text/resources/sk/CollationData_sk.java \
+                sun/text/resources/sl/CollationData_sl.java \
+                sun/text/resources/sq/CollationData_sq.java \
+                sun/text/resources/sr/CollationData_sr.java \
+                sun/text/resources/sr/CollationData_sr_Latn.java \
+                sun/text/resources/sv/CollationData_sv.java \
 		sun/text/resources/th/CollationData_th.java \
+                sun/text/resources/tr/CollationData_tr.java \
+                sun/text/resources/uk/CollationData_uk.java \
 		sun/text/resources/vi/CollationData_vi.java \
 		sun/text/resources/zh/CollationData_zh.java \
 		sun/text/resources/zh/CollationData_zh_HK.java \
@@ -50,15 +78,130 @@
 		sun/text/resources/ar/FormatData_ar_JO.java \
 		sun/text/resources/ar/FormatData_ar_LB.java \
 		sun/text/resources/ar/FormatData_ar_SY.java \
+                sun/text/resources/be/FormatData_be.java \
+                sun/text/resources/be/FormatData_be_BY.java \
+                sun/text/resources/bg/FormatData_bg.java \
+                sun/text/resources/bg/FormatData_bg_BG.java \
+                sun/text/resources/ca/FormatData_ca.java \
+                sun/text/resources/ca/FormatData_ca_ES.java \
+                sun/text/resources/cs/FormatData_cs.java \
+                sun/text/resources/cs/FormatData_cs_CZ.java \
+                sun/text/resources/da/FormatData_da.java \
+                sun/text/resources/da/FormatData_da_DK.java \
+                sun/text/resources/de/FormatData_de.java \
+                sun/text/resources/de/FormatData_de_AT.java \
+                sun/text/resources/de/FormatData_de_CH.java \
+                sun/text/resources/de/FormatData_de_DE.java \
+                sun/text/resources/de/FormatData_de_LU.java \
+                sun/text/resources/el/FormatData_el.java \
+                sun/text/resources/el/FormatData_el_CY.java \
+                sun/text/resources/el/FormatData_el_GR.java \
+                sun/text/resources/en/FormatData_en_AU.java \
+                sun/text/resources/en/FormatData_en_CA.java \
+                sun/text/resources/en/FormatData_en_GB.java \
+                sun/text/resources/en/FormatData_en_IE.java \
+                sun/text/resources/en/FormatData_en_IN.java \
+                sun/text/resources/en/FormatData_en_MT.java \
+                sun/text/resources/en/FormatData_en_NZ.java \
+                sun/text/resources/en/FormatData_en_PH.java \
+                sun/text/resources/en/FormatData_en_SG.java \
+                sun/text/resources/en/FormatData_en_ZA.java \
+                sun/text/resources/es/FormatData_es.java \
+                sun/text/resources/es/FormatData_es_BO.java \
+                sun/text/resources/es/FormatData_es_AR.java \
+                sun/text/resources/es/FormatData_es_CL.java \
+                sun/text/resources/es/FormatData_es_CO.java \
+                sun/text/resources/es/FormatData_es_CR.java \
+                sun/text/resources/es/FormatData_es_DO.java \
+                sun/text/resources/es/FormatData_es_EC.java \
+                sun/text/resources/es/FormatData_es_ES.java \
+                sun/text/resources/es/FormatData_es_GT.java \
+                sun/text/resources/es/FormatData_es_HN.java \
+                sun/text/resources/es/FormatData_es_MX.java \
+                sun/text/resources/es/FormatData_es_NI.java \
+                sun/text/resources/es/FormatData_es_PA.java \
+                sun/text/resources/es/FormatData_es_PE.java \
+                sun/text/resources/es/FormatData_es_PR.java \
+                sun/text/resources/es/FormatData_es_PY.java \
+                sun/text/resources/es/FormatData_es_SV.java \
+                sun/text/resources/es/FormatData_es_US.java \
+                sun/text/resources/es/FormatData_es_UY.java \
+                sun/text/resources/es/FormatData_es_VE.java \
+                sun/text/resources/et/FormatData_et.java \
+                sun/text/resources/et/FormatData_et_EE.java \
+                sun/text/resources/fi/FormatData_fi.java \
+                sun/text/resources/fi/FormatData_fi_FI.java \
+                sun/text/resources/fr/FormatData_fr.java \
+                sun/text/resources/fr/FormatData_fr_BE.java \
+                sun/text/resources/fr/FormatData_fr_CA.java \
+                sun/text/resources/fr/FormatData_fr_CH.java \
+                sun/text/resources/fr/FormatData_fr_FR.java \
+                sun/text/resources/ga/FormatData_ga.java \
+                sun/text/resources/ga/FormatData_ga_IE.java \
                 sun/text/resources/hi/FormatData_hi_IN.java \
+                sun/text/resources/hr/FormatData_hr.java \
+                sun/text/resources/hr/FormatData_hr_HR.java \
+                sun/text/resources/hu/FormatData_hu.java \
+                sun/text/resources/hu/FormatData_hu_HU.java \
+                sun/text/resources/in/FormatData_in.java \
+                sun/text/resources/in/FormatData_in_ID.java \
+                sun/text/resources/is/FormatData_is.java \
+                sun/text/resources/is/FormatData_is_IS.java \
+                sun/text/resources/it/FormatData_it.java \
+                sun/text/resources/it/FormatData_it_CH.java \
+                sun/text/resources/it/FormatData_it_IT.java \
 		sun/text/resources/iw/FormatData_iw.java \
 		sun/text/resources/iw/FormatData_iw_IL.java \
 		sun/text/resources/ja/FormatData_ja.java \
 		sun/text/resources/ja/FormatData_ja_JP.java \
 		sun/text/resources/ko/FormatData_ko.java \
 		sun/text/resources/ko/FormatData_ko_KR.java \
+                sun/text/resources/lt/FormatData_lt.java \
+                sun/text/resources/lt/FormatData_lt_LT.java \
+                sun/text/resources/lv/FormatData_lv.java \
+                sun/text/resources/lv/FormatData_lv_LV.java \
+                sun/text/resources/mk/FormatData_mk.java \
+                sun/text/resources/mk/FormatData_mk_MK.java \
+                sun/text/resources/ms/FormatData_ms.java \
+                sun/text/resources/ms/FormatData_ms_MY.java \
+                sun/text/resources/mt/FormatData_mt.java \
+                sun/text/resources/mt/FormatData_mt_MT.java \
+                sun/text/resources/nl/FormatData_nl.java \
+                sun/text/resources/nl/FormatData_nl_BE.java \
+                sun/text/resources/nl/FormatData_nl_NL.java \
+                sun/text/resources/no/FormatData_no.java \
+                sun/text/resources/no/FormatData_no_NO.java \
+                sun/text/resources/no/FormatData_no_NO_NY.java \
+                sun/text/resources/pl/FormatData_pl.java \
+                sun/text/resources/pl/FormatData_pl_PL.java \
+                sun/text/resources/pt/FormatData_pt.java \
+                sun/text/resources/pt/FormatData_pt_BR.java \
+                sun/text/resources/pt/FormatData_pt_PT.java \
+                sun/text/resources/ro/FormatData_ro.java \
+                sun/text/resources/ro/FormatData_ro_RO.java \
+                sun/text/resources/ru/FormatData_ru.java \
+                sun/text/resources/ru/FormatData_ru_RU.java \
+                sun/text/resources/sk/FormatData_sk.java \
+                sun/text/resources/sk/FormatData_sk_SK.java \
+                sun/text/resources/sl/FormatData_sl.java \
+                sun/text/resources/sl/FormatData_sl_SI.java \
+                sun/text/resources/sq/FormatData_sq.java \
+                sun/text/resources/sq/FormatData_sq_AL.java \
+                sun/text/resources/sr/FormatData_sr.java \
+                sun/text/resources/sr/FormatData_sr_BA.java \
+                sun/text/resources/sr/FormatData_sr_CS.java \
+                sun/text/resources/sr/FormatData_sr_ME.java \
+                sun/text/resources/sr/FormatData_sr_RS.java \
+                sun/text/resources/sr/FormatData_sr_Latn.java \
+                sun/text/resources/sr/FormatData_sr_Latn_ME.java \
+                sun/text/resources/sv/FormatData_sv.java \
+                sun/text/resources/sv/FormatData_sv_SE.java \
 		sun/text/resources/th/FormatData_th.java \
 		sun/text/resources/th/FormatData_th_TH.java \
+                sun/text/resources/tr/FormatData_tr.java \
+                sun/text/resources/tr/FormatData_tr_TR.java \
+                sun/text/resources/uk/FormatData_uk.java \
+                sun/text/resources/uk/FormatData_uk_UA.java \
 		sun/text/resources/vi/FormatData_vi.java \
 		sun/text/resources/vi/FormatData_vi_VN.java \
 		sun/text/resources/zh/FormatData_zh.java \
@@ -70,9 +213,18 @@
                 sun/util/resources/zh/CurrencyNames_zh_HK.java \
                 sun/util/resources/zh/CurrencyNames_zh_SG.java \
                 sun/util/resources/zh/LocaleNames_zh_HK.java \
+                sun/util/resources/de/TimeZoneNames_de.java \
+                sun/util/resources/en/TimeZoneNames_en_CA.java \
+                sun/util/resources/en/TimeZoneNames_en_GB.java \
+                sun/util/resources/en/TimeZoneNames_en_IE.java \
+                sun/util/resources/es/TimeZoneNames_es.java \
+                sun/util/resources/fr/TimeZoneNames_fr.java \
                 sun/util/resources/hi/TimeZoneNames_hi.java \
+                sun/util/resources/it/TimeZoneNames_it.java \
 		sun/util/resources/ja/TimeZoneNames_ja.java \
 		sun/util/resources/ko/TimeZoneNames_ko.java \
+                sun/util/resources/pt/TimeZoneNames_pt_BR.java \
+                sun/util/resources/sv/TimeZoneNames_sv.java \
 		sun/util/resources/zh/TimeZoneNames_zh_CN.java \
 		sun/util/resources/zh/TimeZoneNames_zh_TW.java \
 		sun/util/resources/zh/TimeZoneNames_zh_HK.java
--- a/make/sun/text/FILES_properties.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/sun/text/FILES_properties.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -25,22 +25,112 @@
 
 FILES_compiled_properties = \
         sun/util/resources/ar/LocaleNames_ar.properties \
+        sun/util/resources/be/LocaleNames_be.properties \
+        sun/util/resources/bg/LocaleNames_bg.properties \
+        sun/util/resources/ca/LocaleNames_ca.properties \
+        sun/util/resources/cs/LocaleNames_cs.properties \
+        sun/util/resources/da/LocaleNames_da.properties \
+        sun/util/resources/de/LocaleNames_de.properties \
+        sun/util/resources/el/LocaleNames_el.properties \
+        sun/util/resources/el/LocaleNames_el_CY.properties \
+        sun/util/resources/en/LocaleNames_en_MT.properties \
+        sun/util/resources/en/LocaleNames_en_PH.properties \
+        sun/util/resources/en/LocaleNames_en_SG.properties \
+        sun/util/resources/es/LocaleNames_es.properties \
+        sun/util/resources/es/LocaleNames_es_US.properties \
+        sun/util/resources/et/LocaleNames_et.properties \
+        sun/util/resources/fi/LocaleNames_fi.properties \
+        sun/util/resources/fr/LocaleNames_fr.properties \
+        sun/util/resources/ga/LocaleNames_ga.properties \
         sun/util/resources/hi/LocaleNames_hi.properties \
+        sun/util/resources/hr/LocaleNames_hr.properties \
+        sun/util/resources/hu/LocaleNames_hu.properties \
+        sun/util/resources/in/LocaleNames_in.properties \
+        sun/util/resources/is/LocaleNames_is.properties \
+        sun/util/resources/it/LocaleNames_it.properties \
         sun/util/resources/iw/LocaleNames_iw.properties \
         sun/util/resources/ja/LocaleNames_ja.properties \
         sun/util/resources/ko/LocaleNames_ko.properties \
+        sun/util/resources/lt/LocaleNames_lt.properties \
+        sun/util/resources/lv/LocaleNames_lv.properties \
+        sun/util/resources/mk/LocaleNames_mk.properties \
+        sun/util/resources/ms/LocaleNames_ms.properties \
+        sun/util/resources/mt/LocaleNames_mt.properties \
+        sun/util/resources/nl/LocaleNames_nl.properties \
+        sun/util/resources/no/LocaleNames_no.properties \
+        sun/util/resources/no/LocaleNames_no_NO_NY.properties \
+        sun/util/resources/pl/LocaleNames_pl.properties \
+        sun/util/resources/pt/LocaleNames_pt.properties \
+        sun/util/resources/pt/LocaleNames_pt_BR.properties \
+        sun/util/resources/pt/LocaleNames_pt_PT.properties \
+        sun/util/resources/ro/LocaleNames_ro.properties \
+        sun/util/resources/ru/LocaleNames_ru.properties \
+        sun/util/resources/sk/LocaleNames_sk.properties \
+        sun/util/resources/sl/LocaleNames_sl.properties \
+        sun/util/resources/sq/LocaleNames_sq.properties \
+        sun/util/resources/sr/LocaleNames_sr.properties \
+        sun/util/resources/sr/LocaleNames_sr_Latn.properties \
+        sun/util/resources/sv/LocaleNames_sv.properties \
         sun/util/resources/th/LocaleNames_th.properties \
+        sun/util/resources/tr/LocaleNames_tr.properties \
+        sun/util/resources/uk/LocaleNames_uk.properties \
         sun/util/resources/vi/LocaleNames_vi.properties \
         sun/util/resources/zh/LocaleNames_zh.properties \
         sun/util/resources/zh/LocaleNames_zh_SG.properties \
         sun/util/resources/zh/LocaleNames_zh_TW.properties \
 	\
         sun/util/resources/ar/CalendarData_ar.properties \
+        sun/util/resources/be/CalendarData_be.properties \
+        sun/util/resources/bg/CalendarData_bg.properties \
+        sun/util/resources/ca/CalendarData_ca.properties \
+        sun/util/resources/cs/CalendarData_cs.properties \
+        sun/util/resources/da/CalendarData_da.properties \
+        sun/util/resources/de/CalendarData_de.properties \
+        sun/util/resources/el/CalendarData_el.properties \
+        sun/util/resources/el/CalendarData_el_CY.properties \
+        sun/util/resources/en/CalendarData_en_GB.properties \
+        sun/util/resources/en/CalendarData_en_IE.properties \
+        sun/util/resources/en/CalendarData_en_MT.properties \
+        sun/util/resources/es/CalendarData_es.properties \
+        sun/util/resources/es/CalendarData_es_ES.properties \
+        sun/util/resources/es/CalendarData_es_US.properties \
+        sun/util/resources/et/CalendarData_et.properties \
+        sun/util/resources/fi/CalendarData_fi.properties \
+        sun/util/resources/fr/CalendarData_fr.properties \
+        sun/util/resources/fr/CalendarData_fr_CA.properties \
         sun/util/resources/hi/CalendarData_hi.properties \
+        sun/util/resources/hr/CalendarData_hr.properties \
+        sun/util/resources/hu/CalendarData_hu.properties \
+        sun/util/resources/in/CalendarData_in_ID.properties \
+        sun/util/resources/is/CalendarData_is.properties \
+        sun/util/resources/it/CalendarData_it.properties \
         sun/util/resources/iw/CalendarData_iw.properties \
         sun/util/resources/ja/CalendarData_ja.properties \
         sun/util/resources/ko/CalendarData_ko.properties \
+        sun/util/resources/lt/CalendarData_lt.properties \
+        sun/util/resources/lv/CalendarData_lv.properties \
+        sun/util/resources/mk/CalendarData_mk.properties \
+        sun/util/resources/ms/CalendarData_ms_MY.properties \
+        sun/util/resources/mt/CalendarData_mt.properties \
+        sun/util/resources/mt/CalendarData_mt_MT.properties \
+        sun/util/resources/nl/CalendarData_nl.properties \
+        sun/util/resources/no/CalendarData_no.properties \
+        sun/util/resources/pl/CalendarData_pl.properties \
+        sun/util/resources/pt/CalendarData_pt.properties \
+        sun/util/resources/pt/CalendarData_pt_PT.properties \
+        sun/util/resources/ro/CalendarData_ro.properties \
+        sun/util/resources/ru/CalendarData_ru.properties \
+        sun/util/resources/sk/CalendarData_sk.properties \
+        sun/util/resources/sl/CalendarData_sl.properties \
+        sun/util/resources/sq/CalendarData_sq.properties \
+        sun/util/resources/sr/CalendarData_sr.properties \
+        sun/util/resources/sr/CalendarData_sr_Latn_BA.properties \
+        sun/util/resources/sr/CalendarData_sr_Latn_ME.properties \
+        sun/util/resources/sr/CalendarData_sr_Latn_RS.properties \
+        sun/util/resources/sv/CalendarData_sv.properties \
         sun/util/resources/th/CalendarData_th.properties \
+        sun/util/resources/tr/CalendarData_tr.properties \
+        sun/util/resources/uk/CalendarData_uk.properties \
         sun/util/resources/vi/CalendarData_vi.properties \
         sun/util/resources/zh/CalendarData_zh.properties \
 	\
@@ -61,13 +151,102 @@
         sun/util/resources/ar/CurrencyNames_ar_SY.properties \
         sun/util/resources/ar/CurrencyNames_ar_TN.properties \
         sun/util/resources/ar/CurrencyNames_ar_YE.properties \
+        sun/util/resources/be/CurrencyNames_be_BY.properties \
+        sun/util/resources/bg/CurrencyNames_bg_BG.properties \
+        sun/util/resources/ca/CurrencyNames_ca_ES.properties \
+        sun/util/resources/cs/CurrencyNames_cs_CZ.properties \
+        sun/util/resources/da/CurrencyNames_da_DK.properties \
+        sun/util/resources/de/CurrencyNames_de.properties \
+        sun/util/resources/de/CurrencyNames_de_AT.properties \
+        sun/util/resources/de/CurrencyNames_de_CH.properties \
+        sun/util/resources/de/CurrencyNames_de_DE.properties \
+        sun/util/resources/de/CurrencyNames_de_GR.properties \
+        sun/util/resources/de/CurrencyNames_de_LU.properties \
+        sun/util/resources/el/CurrencyNames_el_CY.properties \
+        sun/util/resources/el/CurrencyNames_el_GR.properties \
+        sun/util/resources/en/CurrencyNames_en_AU.properties \
+        sun/util/resources/en/CurrencyNames_en_CA.properties \
+        sun/util/resources/en/CurrencyNames_en_GB.properties \
+        sun/util/resources/en/CurrencyNames_en_IE.properties \
+        sun/util/resources/en/CurrencyNames_en_IN.properties \
+        sun/util/resources/en/CurrencyNames_en_MT.properties \
+        sun/util/resources/en/CurrencyNames_en_NZ.properties \
+        sun/util/resources/en/CurrencyNames_en_PH.properties \
+        sun/util/resources/en/CurrencyNames_en_SG.properties \
+        sun/util/resources/en/CurrencyNames_en_ZA.properties \
+        sun/util/resources/es/CurrencyNames_es.properties \
+        sun/util/resources/es/CurrencyNames_es_AR.properties \
+        sun/util/resources/es/CurrencyNames_es_BO.properties \
+        sun/util/resources/es/CurrencyNames_es_CL.properties \
+        sun/util/resources/es/CurrencyNames_es_CO.properties \
+        sun/util/resources/es/CurrencyNames_es_CR.properties \
+        sun/util/resources/es/CurrencyNames_es_CU.properties \
+        sun/util/resources/es/CurrencyNames_es_DO.properties \
+        sun/util/resources/es/CurrencyNames_es_EC.properties \
+        sun/util/resources/es/CurrencyNames_es_ES.properties \
+        sun/util/resources/es/CurrencyNames_es_GT.properties \
+        sun/util/resources/es/CurrencyNames_es_HN.properties \
+        sun/util/resources/es/CurrencyNames_es_MX.properties \
+        sun/util/resources/es/CurrencyNames_es_NI.properties \
+        sun/util/resources/es/CurrencyNames_es_PA.properties \
+        sun/util/resources/es/CurrencyNames_es_PE.properties \
+        sun/util/resources/es/CurrencyNames_es_PR.properties \
+        sun/util/resources/es/CurrencyNames_es_PY.properties \
+        sun/util/resources/es/CurrencyNames_es_SV.properties \
+        sun/util/resources/es/CurrencyNames_es_US.properties \
+        sun/util/resources/es/CurrencyNames_es_UY.properties \
+        sun/util/resources/es/CurrencyNames_es_VE.properties \
+        sun/util/resources/et/CurrencyNames_et_EE.properties \
+        sun/util/resources/fi/CurrencyNames_fi_FI.properties \
+        sun/util/resources/fr/CurrencyNames_fr.properties \
+        sun/util/resources/fr/CurrencyNames_fr_BE.properties \
+        sun/util/resources/fr/CurrencyNames_fr_CA.properties \
+        sun/util/resources/fr/CurrencyNames_fr_CH.properties \
+        sun/util/resources/fr/CurrencyNames_fr_FR.properties \
+        sun/util/resources/fr/CurrencyNames_fr_LU.properties \
+        sun/util/resources/ga/CurrencyNames_ga_IE.properties \
         sun/util/resources/hi/CurrencyNames_hi_IN.properties \
+        sun/util/resources/hr/CurrencyNames_hr_HR.properties \
+        sun/util/resources/hu/CurrencyNames_hu_HU.properties \
+        sun/util/resources/in/CurrencyNames_in_ID.properties \
+        sun/util/resources/is/CurrencyNames_is_IS.properties \
+        sun/util/resources/it/CurrencyNames_it.properties \
+        sun/util/resources/it/CurrencyNames_it_CH.properties \
+        sun/util/resources/it/CurrencyNames_it_IT.properties \
         sun/util/resources/iw/CurrencyNames_iw_IL.properties \
         sun/util/resources/ja/CurrencyNames_ja.properties \
         sun/util/resources/ja/CurrencyNames_ja_JP.properties \
         sun/util/resources/ko/CurrencyNames_ko.properties \
         sun/util/resources/ko/CurrencyNames_ko_KR.properties \
+        sun/util/resources/lt/CurrencyNames_lt_LT.properties \
+        sun/util/resources/lv/CurrencyNames_lv_LV.properties \
+        sun/util/resources/mk/CurrencyNames_mk_MK.properties \
+        sun/util/resources/ms/CurrencyNames_ms_MY.properties \
+        sun/util/resources/mt/CurrencyNames_mt_MT.properties \
+        sun/util/resources/nl/CurrencyNames_nl_BE.properties \
+        sun/util/resources/nl/CurrencyNames_nl_NL.properties \
+        sun/util/resources/no/CurrencyNames_no_NO.properties \
+        sun/util/resources/pl/CurrencyNames_pl_PL.properties \
+        sun/util/resources/pt/CurrencyNames_pt.properties \
+        sun/util/resources/pt/CurrencyNames_pt_BR.properties \
+        sun/util/resources/pt/CurrencyNames_pt_PT.properties \
+        sun/util/resources/ro/CurrencyNames_ro_RO.properties \
+        sun/util/resources/ru/CurrencyNames_ru_RU.properties \
+        sun/util/resources/sk/CurrencyNames_sk_SK.properties \
+        sun/util/resources/sl/CurrencyNames_sl_SI.properties \
+        sun/util/resources/sq/CurrencyNames_sq_AL.properties \
+        sun/util/resources/sr/CurrencyNames_sr_BA.properties \
+        sun/util/resources/sr/CurrencyNames_sr_CS.properties \
+        sun/util/resources/sr/CurrencyNames_sr_ME.properties \
+        sun/util/resources/sr/CurrencyNames_sr_RS.properties \
+        sun/util/resources/sr/CurrencyNames_sr_Latn_BA.properties \
+        sun/util/resources/sr/CurrencyNames_sr_Latn_ME.properties \
+        sun/util/resources/sr/CurrencyNames_sr_Latn_RS.properties \
+        sun/util/resources/sv/CurrencyNames_sv.properties \
+        sun/util/resources/sv/CurrencyNames_sv_SE.properties \
         sun/util/resources/th/CurrencyNames_th_TH.properties \
+        sun/util/resources/tr/CurrencyNames_tr_TR.properties \
+        sun/util/resources/uk/CurrencyNames_uk_UA.properties \
         sun/util/resources/vi/CurrencyNames_vi_VN.properties \
         sun/util/resources/zh/CurrencyNames_zh_CN.properties \
         sun/util/resources/zh/CurrencyNames_zh_TW.properties
--- a/make/tools/freetypecheck/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/tools/freetypecheck/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -37,11 +37,11 @@
 
 # Start with CFLAGS (which gets us the required -xarch setting on solaris)
 ifeq ($(PLATFORM), windows)
-  FT_OPTIONS  = /nologo /c
+  FT_OPTIONS  = -nologo -c
   FREETYPE_DLL = $(FREETYPE_LIB_PATH)/freetype.dll
   FT_LD_OPTIONS  = $(FREETYPE_LIB_PATH)/freetype.lib
   ifdef MT
-    FT_LD_OPTIONS += /manifest
+    FT_LD_OPTIONS += -manifest
   endif
 else
   FT_OPTIONS  = $(CFLAGS)
@@ -72,11 +72,11 @@
 	$(prep-target)
 ifeq ($(PLATFORM), windows)
 	$(CC) $(FT_OPTIONS) $(CC_OBJECT_OUTPUT_FLAG)$(FT_OBJ) $<
-	$(LINK) $(FT_LD_OPTIONS) /OUT:$(FT_TEST) $(FT_OBJ)
+	$(LINK) $(FT_LD_OPTIONS) -OUT:$(FT_TEST) $(FT_OBJ)
 	$(CP) $(FREETYPE_DLL) $(@D)/
   ifdef MT
 	$(CP) $(MSVCRNN_DLL_PATH)/$(MSVCRNN_DLL) $(@D)/
-	$(MT) /manifest $(FT_TEST).manifest /outputresource:$(FT_TEST);#1
+	$(MT) -manifest $(FT_TEST).manifest -outputresource:$(FT_TEST);#1
   endif
 else
 	@$(CC) $(FT_OPTIONS) -o $@ $< $(FT_LD_OPTIONS)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/msys_build_scripts/dospath.sh	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,42 @@
+#
+# Copyright (c) 2012, 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.
+#
+
+# A shell script which converts its first argument, which must be an existing 
+# path name, into a DOS (aka 8.3) path name. If the path is a file, only the 
+# directory part of the whole path will be converted.
+# This shell script executes the Visual Basic helper script 'dospath.vbs'
+# which must be located in the same directory as this script itself.
+# The Visual Basic script will be invoked trough the "Windows Script Host"
+# which is available by default on Windows since Windows 98.
+
+pushd `dirname "$0"` > /dev/null
+ABS_PATH=`pwd`
+popd > /dev/null
+if [ -d "$1" ]; then
+  echo `cd "$1" && cscript.exe -nologo $ABS_PATH/dospath.vbs`;
+elif [ -f "$1" ]; then
+  DIR=`dirname "$1"`;
+  echo `cd "$DIR" && cscript.exe -nologo $ABS_PATH/dospath.vbs`\\`basename "$1"`;
+fi
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/msys_build_scripts/dospath.vbs	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,34 @@
+'
+' Copyright (c) 2012, 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.
+'
+
+'
+' Visual Basic Script which returns the DOS (aka 8.3) filename of the current
+' directory.
+' Only called from 'dospath.sh' during a Windows build under MinGW/MSYS.
+'
+
+Set fso=CreateObject("Scripting.FileSystemObject")
+Set path = fso.GetFolder(".")
+WScript.Echo path.ShortPath
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/AbstractGradient.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.bind.annotation.XmlElement;
+
+class AbstractGradient extends Paint {
+    public static enum CycleMethod {
+        NO_CYCLE, REFLECT, REPEAT
+    }
+
+    @XmlElement(name="stop") private ArrayList<GradientStop> stops;
+    public List<GradientStop> getStops() { return stops; }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Border.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlEnumValue;
+
+class Border {
+    enum BorderType {
+        @XmlEnumValue("empty") EMPTY,
+        @XmlEnumValue("painter") PAINTER
+    }
+    @XmlAttribute private BorderType type;
+    @XmlAttribute private String painter;
+    @XmlAttribute private int top;
+    @XmlAttribute private int left;
+    @XmlAttribute private int bottom;
+    @XmlAttribute private int right;
+
+    public String write() {
+        switch (type) {
+            case PAINTER:
+                return String.format("new PainterBorder(\"%s\", new Insets(%d, %d, %d, %d))",
+                                     painter, top, left, bottom, right);
+            case EMPTY:
+                return String.format("BorderFactory.createEmptyBorder(%d, %d, %d, %d)",
+                                     top, left, bottom, right);
+            default:
+                return "### Look, here's an unknown border! $$$";
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Canvas.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.List;
+
+import javax.xml.bind.annotation.XmlElement;
+
+class Canvas {
+    @XmlElement private Dimension size;
+    public Dimension getSize() { return size; }
+
+    @XmlElement(name="layer") private List<Layer> layers;
+    public List<Layer> getLayers() { return layers; }
+
+    @XmlElement private Insets stretchingInsets = null;
+    public Insets getStretchingInsets() { return stretchingInsets; }
+
+    public boolean isBlank() {
+        return layers.size() == 0 || (layers.size() == 1 && layers.get(0).isEmpty());
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/ComponentColor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,93 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+class ComponentColor {
+    private String propertyName;
+    private String defaultColorVariableName;
+    private float saturationOffset = 0,  brightnessOffset = 0;
+    private int alphaOffset = 0;
+
+    ComponentColor(String propertyName,
+            String defaultColorVariableName,
+            float saturationOffset,
+            float brightnessOffset,
+            int alphaOffset) {
+        this.propertyName = propertyName;
+        this.defaultColorVariableName = defaultColorVariableName;
+        this.saturationOffset = saturationOffset;
+        this.brightnessOffset = brightnessOffset;
+        this.alphaOffset = alphaOffset;
+    }
+
+    @Override
+    public boolean equals(Object o) {
+        if (this == o) {
+            return true;
+        }
+        if (o == null || getClass() != o.getClass()) {
+            return false;
+        }
+
+        ComponentColor c = (ComponentColor) o;
+        if (alphaOffset != c.alphaOffset) {
+            return false;
+        }
+        if (Float.compare(saturationOffset, c.saturationOffset) != 0) {
+            return false;
+        }
+        if (Float.compare(brightnessOffset, c.brightnessOffset) != 0) {
+            return false;
+        }
+        if (defaultColorVariableName != null ? !defaultColorVariableName.equals(c.defaultColorVariableName) : c.defaultColorVariableName != null) {
+            return false;
+        }
+        if (propertyName != null ? !propertyName.equals(c.propertyName) : c.propertyName != null) {
+            return false;
+        }
+        return true;
+    }
+
+    @Override
+    public int hashCode() {
+        int hash = 5;
+        hash = 61 * hash + (this.propertyName != null ? this.propertyName.hashCode() : 0);
+        hash = 61 * hash + (this.defaultColorVariableName != null ? this.defaultColorVariableName.hashCode() : 0);
+        hash = 61 * hash + Float.floatToIntBits(this.saturationOffset);
+        hash = 61 * hash + Float.floatToIntBits(this.brightnessOffset);
+        hash = 61 * hash + this.alphaOffset;
+        return hash;
+    }
+
+    public void write(StringBuilder sb) {
+        sb.append("                     getComponentColor(c, \"").
+           append(propertyName).append("\", ").
+           append(defaultColorVariableName).append(", ").
+           append(saturationOffset).append("f, ").
+           append(brightnessOffset).append("f, ").
+           append(alphaOffset);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Dimension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,38 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Dimension {
+    @XmlAttribute int width;
+    @XmlAttribute int height;
+
+    public String write(boolean uiResource) {
+        String uiSuffix = (uiResource ? "UIResource" : "");
+        return String.format("new Dimension%s(%d, %d)", uiSuffix, width, height);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Ellipse.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Ellipse extends Shape {
+    @XmlAttribute private double x1;
+    public double getX1() { return x1; }
+
+    @XmlAttribute private double x2;
+    public double getX2() { return x2; }
+
+    @XmlAttribute private double y1;
+    public double getY1() { return y1; }
+
+    @XmlAttribute private double y2;
+    public double getY2() { return y2; }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Gradient.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+class Gradient extends AbstractGradient {
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/GradientStop.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+
+class GradientStop {
+    @XmlAttribute private float position;
+    public float getPosition() { return position; }
+
+    @XmlAttribute private float midpoint;
+    public float getMidpoint() { return midpoint; }
+
+    @XmlElement private Matte matte;
+    public Matte getColor() { return matte; }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Insets.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Insets {
+    @XmlAttribute int top;
+    @XmlAttribute int left;
+    @XmlAttribute int bottom;
+    @XmlAttribute int right;
+
+    public Insets() {
+        this(0, 0, 0, 0);
+    }
+
+    public Insets(int top, int left, int bottom, int right) {
+        this.top = top;
+        this.left = left;
+        this.bottom = bottom;
+        this.right = right;
+    }
+
+    public String write(boolean uiResource) {
+        String uiSuffix = (uiResource ? "UIResource" : "");
+        return String.format("new Insets%s(%d, %d, %d, %d)",
+                             uiSuffix, top, left, bottom, right);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Layer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlElementWrapper;
+import javax.xml.bind.annotation.XmlElements;
+
+class Layer {
+    /** List of shapes in this layer, first shape is painted on top */
+    @XmlElements({
+        @XmlElement(name = "ellipse", type = Ellipse.class),
+        @XmlElement(name = "path", type = Path.class),
+        @XmlElement(name = "rectangle", type = Rectangle.class)
+    })
+    @XmlElementWrapper(name="shapes")
+    private List<Shape> shapes = new ArrayList<Shape>();
+    public List<Shape> getShapes() { return shapes; }
+
+    public boolean isEmpty() {
+        return shapes.isEmpty();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Matte.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,82 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Matte extends Paint {
+    @XmlAttribute private int red;
+    @XmlAttribute private int green;
+    @XmlAttribute private int blue;
+    @XmlAttribute private int alpha;
+
+    @XmlAttribute private String uiDefaultParentName = null;
+    @XmlAttribute private float hueOffset = 0;
+    @XmlAttribute private float saturationOffset = 0;
+    @XmlAttribute private float brightnessOffset = 0;
+    @XmlAttribute private int alphaOffset = 0;
+
+    @XmlAttribute private String componentPropertyName = null;
+    public String getComponentPropertyName() { return componentPropertyName; }
+
+    @XmlAttribute private boolean uiResource = true;
+
+    public boolean isAbsolute() {
+        return uiDefaultParentName == null;
+    }
+
+    public String getDeclaration() {
+        if (isAbsolute()) {
+            return String.format("new Color(%d, %d, %d, %d)",
+                                 red, green, blue, alpha);
+        } else {
+            return String.format("decodeColor(\"%s\", %sf, %sf, %sf, %d)",
+                    uiDefaultParentName, String.valueOf(hueOffset),
+                    String.valueOf(saturationOffset),
+                    String.valueOf(brightnessOffset), alphaOffset);
+        }
+    }
+
+    public String write() {
+        if (isAbsolute()) {
+            return String.format("%s, %s, %s, %s", red, green, blue, alpha);
+        } else {
+            String s = String.format("\"%s\", %sf, %sf, %sf, %d",
+                    uiDefaultParentName, String.valueOf(hueOffset),
+                    String.valueOf(saturationOffset),
+                    String.valueOf(brightnessOffset), alphaOffset);
+            if (! uiResource) {
+                s += ", false";
+            }
+            return s;
+        }
+    }
+
+    public ComponentColor createComponentColor(String variableName) {
+        return new ComponentColor(componentPropertyName, variableName,
+                saturationOffset, brightnessOffset, alphaOffset);
+    }
+}
--- a/make/tools/src/build/tools/generatenimbus/Paint.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/tools/src/build/tools/generatenimbus/Paint.java	Mon Nov 05 10:33:18 2012 -0500
@@ -25,157 +25,6 @@
 
 package build.tools.generatenimbus;
 
-import java.util.ArrayList;
-import java.util.List;
-import javax.xml.bind.annotation.XmlAttribute;
-import javax.xml.bind.annotation.XmlElement;
 
 public abstract class Paint {
 }
-
-class Matte extends Paint {
-    @XmlAttribute private int red;
-    @XmlAttribute private int green;
-    @XmlAttribute private int blue;
-    @XmlAttribute private int alpha;
-
-    @XmlAttribute private String uiDefaultParentName = null;
-    @XmlAttribute private float hueOffset = 0;
-    @XmlAttribute private float saturationOffset = 0;
-    @XmlAttribute private float brightnessOffset = 0;
-    @XmlAttribute private int alphaOffset = 0;
-
-    @XmlAttribute private String componentPropertyName = null;
-    public String getComponentPropertyName() { return componentPropertyName; }
-
-    @XmlAttribute private boolean uiResource = true;
-
-    public boolean isAbsolute() {
-        return uiDefaultParentName == null;
-    }
-
-    public String getDeclaration() {
-        if (isAbsolute()) {
-            return String.format("new Color(%d, %d, %d, %d)",
-                                 red, green, blue, alpha);
-        } else {
-            return String.format("decodeColor(\"%s\", %sf, %sf, %sf, %d)",
-                    uiDefaultParentName, String.valueOf(hueOffset),
-                    String.valueOf(saturationOffset),
-                    String.valueOf(brightnessOffset), alphaOffset);
-        }
-    }
-
-    public String write() {
-        if (isAbsolute()) {
-            return String.format("%s, %s, %s, %s", red, green, blue, alpha);
-        } else {
-            String s = String.format("\"%s\", %sf, %sf, %sf, %d",
-                    uiDefaultParentName, String.valueOf(hueOffset),
-                    String.valueOf(saturationOffset),
-                    String.valueOf(brightnessOffset), alphaOffset);
-            if (! uiResource) {
-                s += ", false";
-            }
-            return s;
-        }
-    }
-
-    public ComponentColor createComponentColor(String variableName) {
-        return new ComponentColor(componentPropertyName, variableName,
-                saturationOffset, brightnessOffset, alphaOffset);
-    }
-}
-
-class ComponentColor {
-    private String propertyName;
-    private String defaultColorVariableName;
-    private float saturationOffset = 0,  brightnessOffset = 0;
-    private int alphaOffset = 0;
-
-    ComponentColor(String propertyName,
-            String defaultColorVariableName,
-            float saturationOffset,
-            float brightnessOffset,
-            int alphaOffset) {
-        this.propertyName = propertyName;
-        this.defaultColorVariableName = defaultColorVariableName;
-        this.saturationOffset = saturationOffset;
-        this.brightnessOffset = brightnessOffset;
-        this.alphaOffset = alphaOffset;
-    }
-
-    @Override
-    public boolean equals(Object o) {
-        if (this == o) {
-            return true;
-        }
-        if (o == null || getClass() != o.getClass()) {
-            return false;
-        }
-
-        ComponentColor c = (ComponentColor) o;
-        if (alphaOffset != c.alphaOffset) {
-            return false;
-        }
-        if (Float.compare(saturationOffset, c.saturationOffset) != 0) {
-            return false;
-        }
-        if (Float.compare(brightnessOffset, c.brightnessOffset) != 0) {
-            return false;
-        }
-        if (defaultColorVariableName != null ? !defaultColorVariableName.equals(c.defaultColorVariableName) : c.defaultColorVariableName != null) {
-            return false;
-        }
-        if (propertyName != null ? !propertyName.equals(c.propertyName) : c.propertyName != null) {
-            return false;
-        }
-        return true;
-    }
-
-    @Override
-    public int hashCode() {
-        int hash = 5;
-        hash = 61 * hash + (this.propertyName != null ? this.propertyName.hashCode() : 0);
-        hash = 61 * hash + (this.defaultColorVariableName != null ? this.defaultColorVariableName.hashCode() : 0);
-        hash = 61 * hash + Float.floatToIntBits(this.saturationOffset);
-        hash = 61 * hash + Float.floatToIntBits(this.brightnessOffset);
-        hash = 61 * hash + this.alphaOffset;
-        return hash;
-    }
-
-    public void write(StringBuilder sb) {
-        sb.append("                     getComponentColor(c, \"").
-           append(propertyName).append("\", ").
-           append(defaultColorVariableName).append(", ").
-           append(saturationOffset).append("f, ").
-           append(brightnessOffset).append("f, ").
-           append(alphaOffset);
-    }
-}
-
-class GradientStop {
-    @XmlAttribute private float position;
-    public float getPosition() { return position; }
-
-    @XmlAttribute private float midpoint;
-    public float getMidpoint() { return midpoint; }
-
-    @XmlElement private Matte matte;
-    public Matte getColor() { return matte; }
-}
-
-class AbstractGradient extends Paint {
-    public static enum CycleMethod {
-        NO_CYCLE, REFLECT, REPEAT
-    }
-
-    @XmlElement(name="stop") private ArrayList<GradientStop> stops;
-    public List<GradientStop> getStops() { return stops; }
-}
-
-class Gradient extends AbstractGradient {
-}
-
-class RadialGradient extends AbstractGradient {
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Path.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,39 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlElementWrapper;
+
+class Path extends Shape {
+    @XmlElement(name="point")
+    @XmlElementWrapper(name="points")
+    private List<Point> controlPoints = new ArrayList<Point>();
+    public List<Point> getControlPoints() { return controlPoints; }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Point.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,56 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Point {
+    @XmlAttribute private double x;
+    public double getX() { return x; }
+
+    @XmlAttribute private double y;
+    public double getY() { return y; }
+
+    @XmlAttribute(name="cp1x") private double cp1x;
+    public double getCp1X() { return cp1x; }
+
+    @XmlAttribute(name="cp1y") private double cp1y;
+    public double getCp1Y() { return cp1y; }
+
+    @XmlAttribute(name="cp2x") private double cp2x;
+    public double getCp2X() { return cp2x; }
+
+    @XmlAttribute(name="cp2y") private double cp2y;
+    public double getCp2Y() { return cp2y; }
+
+    public boolean isP1Sharp() {
+        return cp1x == x && cp1y == y;
+    }
+
+    public boolean isP2Sharp() {
+        return cp2x == x && cp2y == y;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/RadialGradient.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,29 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+class RadialGradient extends AbstractGradient {
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Rectangle.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Rectangle extends Shape {
+    @XmlAttribute private double x1;
+    public double getX1() { return x1; }
+
+    @XmlAttribute private double x2;
+    public double getX2() { return x2; }
+
+    @XmlAttribute private double y1;
+    public double getY1() { return y1; }
+
+    @XmlAttribute private double y2;
+    public double getY2() { return y2; }
+
+    @XmlAttribute
+    public double getRounding() {
+        double rounding = Math.abs(roundingX - x1) * 2;
+        return rounding > 2 ? rounding : 0;
+    }
+
+    public void setRounding(double rounding) {
+        if (rounding > 0 && rounding < 2) {
+            rounding = 0;
+        }
+        roundingX = rounding / 2d + x1;
+    }
+    private double roundingX;
+
+    public boolean isRounded() {
+        return getRounding() > 0;
+    }
+
+}
--- a/make/tools/src/build/tools/generatenimbus/Shape.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/tools/src/build/tools/generatenimbus/Shape.java	Mon Nov 05 10:33:18 2012 -0500
@@ -25,11 +25,8 @@
 
 package build.tools.generatenimbus;
 
-import java.util.ArrayList;
-import java.util.List;
 import javax.xml.bind.annotation.XmlAttribute;
 import javax.xml.bind.annotation.XmlElement;
-import javax.xml.bind.annotation.XmlElementWrapper;
 import javax.xml.bind.annotation.XmlElements;
 
 
@@ -56,85 +53,3 @@
         @XmlAttribute double y2;
     }
 }
-
-class Point {
-    @XmlAttribute private double x;
-    public double getX() { return x; }
-
-    @XmlAttribute private double y;
-    public double getY() { return y; }
-
-    @XmlAttribute(name="cp1x") private double cp1x;
-    public double getCp1X() { return cp1x; }
-
-    @XmlAttribute(name="cp1y") private double cp1y;
-    public double getCp1Y() { return cp1y; }
-
-    @XmlAttribute(name="cp2x") private double cp2x;
-    public double getCp2X() { return cp2x; }
-
-    @XmlAttribute(name="cp2y") private double cp2y;
-    public double getCp2Y() { return cp2y; }
-
-    public boolean isP1Sharp() {
-        return cp1x == x && cp1y == y;
-    }
-
-    public boolean isP2Sharp() {
-        return cp2x == x && cp2y == y;
-    }
-}
-
-class Path extends Shape {
-    @XmlElement(name="point")
-    @XmlElementWrapper(name="points")
-    private List<Point> controlPoints = new ArrayList<Point>();
-    public List<Point> getControlPoints() { return controlPoints; }
-}
-
-class Rectangle extends Shape {
-    @XmlAttribute private double x1;
-    public double getX1() { return x1; }
-
-    @XmlAttribute private double x2;
-    public double getX2() { return x2; }
-
-    @XmlAttribute private double y1;
-    public double getY1() { return y1; }
-
-    @XmlAttribute private double y2;
-    public double getY2() { return y2; }
-
-    @XmlAttribute
-    public double getRounding() {
-        double rounding = Math.abs(roundingX - x1) * 2;
-        return rounding > 2 ? rounding : 0;
-    }
-
-    public void setRounding(double rounding) {
-        if (rounding > 0 && rounding < 2) {
-            rounding = 0;
-        }
-        roundingX = rounding / 2d + x1;
-    }
-    private double roundingX;
-
-    public boolean isRounded() {
-        return getRounding() > 0;
-    }
-
-}
-
-class Ellipse extends Shape {
-    @XmlAttribute private double x1;
-    public double getX1() { return x1; }
-
-    @XmlAttribute private double x2;
-    public double getX2() { return x2; }
-
-    @XmlAttribute private double y1;
-    public double getY1() { return y1; }
-
-    @XmlAttribute private double y2;
-    public double getY2() { return y2; }
-}
--- a/make/tools/src/build/tools/generatenimbus/SynthModel.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/tools/src/build/tools/generatenimbus/SynthModel.java	Mon Nov 05 10:33:18 2012 -0500
@@ -25,9 +25,7 @@
 
 package build.tools.generatenimbus;
 
-import java.awt.Font;
 import java.util.ArrayList;
-import java.util.List;
 import javax.xml.bind.annotation.*;
 
 
@@ -78,139 +76,3 @@
         }
     }
 }
-
-class Typeface {
-    public enum DeriveStyle {
-        Default, Off, On;
-
-        @Override public String toString() {
-            switch (this) {
-                default:  return "null";
-                case On:  return "true";
-                case Off: return "false";
-            }
-        }
-    }
-
-    @XmlAttribute private String uiDefaultParentName;
-    @XmlAttribute(name="family") private String name;
-    @XmlAttribute private int size;
-    @XmlAttribute private DeriveStyle bold = DeriveStyle.Default;
-    @XmlAttribute private DeriveStyle italic = DeriveStyle.Default;
-    @XmlAttribute private float sizeOffset = 1f;
-
-    public boolean isAbsolute() {
-        return uiDefaultParentName == null;
-    }
-
-    public String write() {
-        if (isAbsolute()) {
-            int style = Font.PLAIN;
-            if (bold == DeriveStyle.On) {
-                style = style | Font.BOLD;
-            }
-            if (italic == DeriveStyle.On) {
-                style = style | Font.ITALIC;
-            }
-
-            return String.format(
-                    "new javax.swing.plaf.FontUIResource(\"%s\", %d, %d)",
-                    name, style, size);
-        } else {
-            return String.format(
-                    "new DerivedFont(\"%s\", %sf, %s, %s)",
-                    uiDefaultParentName, String.valueOf(sizeOffset), bold, italic);
-        }
-    }
-}
-
-class Border {
-    enum BorderType {
-        @XmlEnumValue("empty") EMPTY,
-        @XmlEnumValue("painter") PAINTER
-    }
-    @XmlAttribute private BorderType type;
-    @XmlAttribute private String painter;
-    @XmlAttribute private int top;
-    @XmlAttribute private int left;
-    @XmlAttribute private int bottom;
-    @XmlAttribute private int right;
-
-    public String write() {
-        switch (type) {
-            case PAINTER:
-                return String.format("new PainterBorder(\"%s\", new Insets(%d, %d, %d, %d))",
-                                     painter, top, left, bottom, right);
-            case EMPTY:
-                return String.format("BorderFactory.createEmptyBorder(%d, %d, %d, %d)",
-                                     top, left, bottom, right);
-            default:
-                return "### Look, here's an unknown border! $$$";
-        }
-    }
-}
-
-class Insets {
-    @XmlAttribute int top;
-    @XmlAttribute int left;
-    @XmlAttribute int bottom;
-    @XmlAttribute int right;
-
-    public Insets() {
-        this(0, 0, 0, 0);
-    }
-
-    public Insets(int top, int left, int bottom, int right) {
-        this.top = top;
-        this.left = left;
-        this.bottom = bottom;
-        this.right = right;
-    }
-
-    public String write(boolean uiResource) {
-        String uiSuffix = (uiResource ? "UIResource" : "");
-        return String.format("new Insets%s(%d, %d, %d, %d)",
-                             uiSuffix, top, left, bottom, right);
-    }
-}
-
-class Dimension {
-    @XmlAttribute int width;
-    @XmlAttribute int height;
-
-    public String write(boolean uiResource) {
-        String uiSuffix = (uiResource ? "UIResource" : "");
-        return String.format("new Dimension%s(%d, %d)", uiSuffix, width, height);
-    }
-}
-
-class Canvas {
-    @XmlElement private Dimension size;
-    public Dimension getSize() { return size; }
-
-    @XmlElement(name="layer") private List<Layer> layers;
-    public List<Layer> getLayers() { return layers; }
-
-    @XmlElement private Insets stretchingInsets = null;
-    public Insets getStretchingInsets() { return stretchingInsets; }
-
-    public boolean isBlank() {
-        return layers.size() == 0 || (layers.size() == 1 && layers.get(0).isEmpty());
-    }
-}
-
-class Layer {
-    /** List of shapes in this layer, first shape is painted on top */
-    @XmlElements({
-        @XmlElement(name = "ellipse", type = Ellipse.class),
-        @XmlElement(name = "path", type = Path.class),
-        @XmlElement(name = "rectangle", type = Rectangle.class)
-    })
-    @XmlElementWrapper(name="shapes")
-    private List<Shape> shapes = new ArrayList<Shape>();
-    public List<Shape> getShapes() { return shapes; }
-
-    public boolean isEmpty() {
-        return shapes.isEmpty();
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/Typeface.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.awt.Font;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class Typeface {
+    public enum DeriveStyle {
+        Default, Off, On;
+
+        @Override public String toString() {
+            switch (this) {
+                default:  return "null";
+                case On:  return "true";
+                case Off: return "false";
+            }
+        }
+    }
+
+    @XmlAttribute private String uiDefaultParentName;
+    @XmlAttribute(name="family") private String name;
+    @XmlAttribute private int size;
+    @XmlAttribute private DeriveStyle bold = DeriveStyle.Default;
+    @XmlAttribute private DeriveStyle italic = DeriveStyle.Default;
+    @XmlAttribute private float sizeOffset = 1f;
+
+    public boolean isAbsolute() {
+        return uiDefaultParentName == null;
+    }
+
+    public String write() {
+        if (isAbsolute()) {
+            int style = Font.PLAIN;
+            if (bold == DeriveStyle.On) {
+                style = style | Font.BOLD;
+            }
+            if (italic == DeriveStyle.On) {
+                style = style | Font.ITALIC;
+            }
+
+            return String.format(
+                    "new javax.swing.plaf.FontUIResource(\"%s\", %d, %d)",
+                    name, style, size);
+        } else {
+            return String.format(
+                    "new DerivedFont(\"%s\", %sf, %s, %s)",
+                    uiDefaultParentName, String.valueOf(sizeOffset), bold, italic);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIColor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlElement;
+
+class UIColor extends UIDefault<Matte> {
+
+    @XmlElement
+    public void setMatte(Matte m) {
+        setValue(m);
+    }
+
+    public String write() {
+        return String.format("        addColor(d, \"%s\", %s);\n",
+                             getName(), getValue().write());
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIComponent.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,54 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlElementWrapper;
+
+class UIComponent extends UIRegion {
+    @XmlAttribute private String componentName;
+
+    @XmlElement(name="stateType")
+    @XmlElementWrapper(name="stateTypes")
+    private List<UIStateType> stateTypes = new ArrayList<UIStateType>();
+    public List<UIStateType> getStateTypes() { return stateTypes; }
+
+    @Override public String getKey() {
+        if (key == null || "".equals(key)) {
+            if (componentName == null || "".equals(componentName)) {
+                return name;
+            } else {
+                return "\"" + componentName + "\"";
+            }
+        } else {
+            return key;
+        }
+    }
+}
--- a/make/tools/src/build/tools/generatenimbus/UIDefault.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/tools/src/build/tools/generatenimbus/UIDefault.java	Mon Nov 05 10:33:18 2012 -0500
@@ -26,7 +26,6 @@
 package build.tools.generatenimbus;
 
 import javax.xml.bind.annotation.XmlAttribute;
-import javax.xml.bind.annotation.XmlElement;
 
 public class UIDefault<T> {
     @XmlAttribute private String name;
@@ -44,83 +43,3 @@
         this.value = value;
     }
 }
-
-class UIColor extends UIDefault<Matte> {
-
-    @XmlElement
-    public void setMatte(Matte m) {
-        setValue(m);
-    }
-
-    public String write() {
-        return String.format("        addColor(d, \"%s\", %s);\n",
-                             getName(), getValue().write());
-    }
-}
-
-class UIFont extends UIDefault<Typeface> {
-    @XmlElement
-    public void setTypeface(Typeface t) {
-        setValue(t);
-    }
-
-    public String write() {
-        return String.format("        d.put(\"%s\", %s);\n",
-                             getName(), getValue().write());
-    }
-}
-
-class UIProperty extends UIDefault<String> {
-    public static enum PropertyType {
-        BOOLEAN, INT, FLOAT, DOUBLE, STRING, FONT, COLOR, INSETS, DIMENSION, BORDER
-    }
-    @XmlAttribute private PropertyType type;
-
-    @XmlElement private Border border;
-    @XmlElement private Dimension dimension;
-    @XmlElement private Insets insets;
-    @XmlElement private Matte matte;
-    @XmlElement private Typeface typeface;
-
-    @XmlAttribute
-    @Override public void setValue(String value) {
-        super.setValue(value);
-    }
-
-    public String write(String prefix) {
-        switch (type) {
-            case BOOLEAN:
-                return String.format("        d.put(\"%s%s\", Boolean.%s);\n",
-                                     prefix, getName(), getValue().toUpperCase());  ///autobox
-            case STRING:
-                return String.format("        d.put(\"%s%s\", \"%s\");\n",
-                                     prefix, getName(), getValue());
-            case INT:
-                return String.format("        d.put(\"%s%s\", new Integer(%s));\n",
-                                     prefix, getName(), getValue());
-            case FLOAT:
-                return String.format("        d.put(\"%s%s\", new Float(%sf));\n",
-                                     prefix, getName(), getValue());
-            case DOUBLE:
-                return String.format("        d.put(\"%s%s\", new Double(%s));\n",
-                                     prefix, getName(), getValue());
-            case COLOR:
-                return String.format("        addColor(d, \"%s%s\", %s);\n",
-                                     prefix, getName(), matte.write());
-            case FONT:
-                return String.format("        d.put(\"%s%s\", %s);\n",
-                                     prefix, getName(), typeface.write());
-            case INSETS:
-                return String.format("        d.put(\"%s%s\", %s);\n",
-                                     prefix, getName(), insets.write(true));
-            case DIMENSION:
-                return String.format("        d.put(\"%s%s\", new DimensionUIResource(%d, %d));\n",
-                                     prefix, getName(), dimension.width, dimension.height);
-            case BORDER:
-                return String.format("        d.put(\"%s%s\", new BorderUIResource(%s));\n",
-                                     prefix, getName(), border.write());
-            default:
-                return "###  Look, something's wrong with UIProperty.write()  $$$";
-        }
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIFont.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlElement;
+
+class UIFont extends UIDefault<Typeface> {
+    @XmlElement
+    public void setTypeface(Typeface t) {
+        setValue(t);
+    }
+
+    public String write() {
+        return String.format("        d.put(\"%s\", %s);\n",
+                             getName(), getValue().write());
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIIconRegion.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+
+class UIIconRegion extends UIRegion {
+    @XmlAttribute private String basicKey;
+
+    @Override public void write(StringBuilder sb, StringBuilder styleBuffer, UIComponent comp, String prefix, String pkg) {
+        Dimension size = null;
+        String fileNamePrefix = Utils.normalize(prefix) + "Painter";
+        // write states ui defaults
+        for (UIState state : backgroundStates) {
+            Canvas canvas = state.getCanvas();
+            if (!canvas.isBlank()) {
+                state.write(sb, prefix, pkg, fileNamePrefix, getKey());
+                size = canvas.getSize();
+            }
+        }
+
+        if (size != null) {
+            // Put SynthIconImpl wrapper in UiDefaults
+            String k = (basicKey == null ? prefix + "." + getKey() : basicKey);
+            sb.append(String.format(
+                    "        d.put(\"%s\", new NimbusIcon(\"%s\", \"%sPainter\", %d, %d));\n",
+                    k, prefix, getKey(), size.width, size.height));
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIProperty.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,84 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+
+class UIProperty extends UIDefault<String> {
+    public static enum PropertyType {
+        BOOLEAN, INT, FLOAT, DOUBLE, STRING, FONT, COLOR, INSETS, DIMENSION, BORDER
+    }
+    @XmlAttribute private PropertyType type;
+
+    @XmlElement private Border border;
+    @XmlElement private Dimension dimension;
+    @XmlElement private Insets insets;
+    @XmlElement private Matte matte;
+    @XmlElement private Typeface typeface;
+
+    @XmlAttribute
+    @Override public void setValue(String value) {
+        super.setValue(value);
+    }
+
+    public String write(String prefix) {
+        switch (type) {
+            case BOOLEAN:
+                return String.format("        d.put(\"%s%s\", Boolean.%s);\n",
+                                     prefix, getName(), getValue().toUpperCase());  ///autobox
+            case STRING:
+                return String.format("        d.put(\"%s%s\", \"%s\");\n",
+                                     prefix, getName(), getValue());
+            case INT:
+                return String.format("        d.put(\"%s%s\", new Integer(%s));\n",
+                                     prefix, getName(), getValue());
+            case FLOAT:
+                return String.format("        d.put(\"%s%s\", new Float(%sf));\n",
+                                     prefix, getName(), getValue());
+            case DOUBLE:
+                return String.format("        d.put(\"%s%s\", new Double(%s));\n",
+                                     prefix, getName(), getValue());
+            case COLOR:
+                return String.format("        addColor(d, \"%s%s\", %s);\n",
+                                     prefix, getName(), matte.write());
+            case FONT:
+                return String.format("        d.put(\"%s%s\", %s);\n",
+                                     prefix, getName(), typeface.write());
+            case INSETS:
+                return String.format("        d.put(\"%s%s\", %s);\n",
+                                     prefix, getName(), insets.write(true));
+            case DIMENSION:
+                return String.format("        d.put(\"%s%s\", new DimensionUIResource(%d, %d));\n",
+                                     prefix, getName(), dimension.width, dimension.height);
+            case BORDER:
+                return String.format("        d.put(\"%s%s\", new BorderUIResource(%s));\n",
+                                     prefix, getName(), border.write());
+            default:
+                return "###  Look, something's wrong with UIProperty.write()  $$$";
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIRegion.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,200 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+import javax.xml.bind.annotation.XmlElementWrapper;
+import javax.xml.bind.annotation.XmlElements;
+
+class UIRegion {
+    @XmlAttribute protected String name;
+    @XmlAttribute protected String key;
+    @XmlAttribute private boolean opaque = false;
+
+    @XmlElement private Insets contentMargins = new Insets(0, 0, 0, 0);
+
+    @XmlElement(name="state")
+    @XmlElementWrapper(name="backgroundStates")
+    protected List<UIState> backgroundStates = new ArrayList<UIState>();
+    public List<UIState> getBackgroundStates() { return backgroundStates; }
+
+    @XmlElement(name="state")
+    @XmlElementWrapper(name="foregroundStates")
+    protected List<UIState> foregroundStates = new ArrayList<UIState>();
+    public List<UIState> getForegroundStates() { return foregroundStates; }
+
+    @XmlElement(name="state")
+    @XmlElementWrapper(name="borderStates")
+    protected List<UIState> borderStates = new ArrayList<UIState>();
+    public List<UIState> getBorderStates() { return borderStates; }
+
+    @XmlElement private UIStyle style = new UIStyle();
+
+    @XmlElements({
+        @XmlElement(name = "region", type = UIRegion.class),
+        @XmlElement(name = "uiComponent", type = UIComponent.class),
+        @XmlElement(name = "uiIconRegion", type = UIIconRegion.class)
+    })
+    @XmlElementWrapper(name="regions")
+    private List<UIRegion> subRegions = new ArrayList<UIRegion>();
+    public List<UIRegion> getSubRegions() { return subRegions; }
+
+    protected void initStyles(UIStyle parentStyle) {
+        style.setParentStyle(parentStyle);
+        for (UIState state: backgroundStates) {
+            state.getStyle().setParentStyle(this.style);
+        }
+        for (UIState state: foregroundStates) {
+            state.getStyle().setParentStyle(this.style);
+        }
+        for (UIState state: borderStates) {
+            state.getStyle().setParentStyle(this.style);
+        }
+        for (UIRegion region: subRegions) {
+            region.initStyles(this.style);
+        }
+    }
+
+    public String getKey() {
+        return key == null || "".equals(key) ? name : key;
+    }
+
+    private boolean hasCanvas() {
+        for (UIState s : backgroundStates) {
+            if (s.hasCanvas()) return true;
+        }
+        for (UIState s : borderStates) {
+            if (s.hasCanvas()) return true;
+        }
+        for (UIState s : foregroundStates) {
+            if (s.hasCanvas()) return true;
+        }
+        for (UIRegion r: subRegions) {
+            if (r.hasCanvas()) return true;
+        }
+        return false;
+    }
+
+    public void write(StringBuilder sb, StringBuilder styleBuffer,
+                      UIComponent comp, String prefix, String pkg) {
+        // write content margins
+        sb.append(String.format("        d.put(\"%s.contentMargins\", %s);\n",
+                                prefix, contentMargins.write(true)));
+        // write opaque if true
+        if (opaque) {
+            sb.append(String.format("        d.put(\"%s.opaque\", Boolean.TRUE);\n", prefix));
+        }
+
+        // register component with LAF
+        String regionCode = "Region." + Utils.regionNameToCaps(name);
+        styleBuffer.append(String.format("        register(%s, \"%s\");\n",
+                                         regionCode, prefix));
+
+        //write the State, if necessary
+        StringBuffer regString = new StringBuffer();
+        List<UIStateType> types = comp.getStateTypes();
+        if (types != null && types.size() > 0) {
+            for (UIStateType type : types) {
+                regString.append(type.getKey());
+                regString.append(",");
+            }
+            //remove the last ","
+            regString.deleteCharAt(regString.length() - 1);
+        }
+
+        if (! regString.equals("Enabled,MouseOver,Pressed,Disabled,Focused,Selected,Default") && types.size() > 0) {
+            //there were either custom states, or the normal states were in a custom order
+            //so go ahead and write out prefix.State
+            sb.append(String.format("        d.put(\"%s.States\", \"%s\");\n",
+                                    prefix, regString));
+        }
+
+        // write out any custom states, if necessary
+        for (UIStateType type : types) {
+            String synthState = type.getKey();
+            if (! "Enabled".equals(synthState) &&
+                ! "MouseOver".equals(synthState) &&
+                ! "Pressed".equals(synthState) &&
+                ! "Disabled".equals(synthState) &&
+                ! "Focused".equals(synthState) &&
+                ! "Selected".equals(synthState) &&
+                ! "Default".equals(synthState)) {
+
+                //what we have here, gentlemen, is a bona-fide custom state.
+                //if the type is not one of the standard types, then construct a name for
+                //the new type, and write out a new subclass of State.
+                String className = Utils.normalize(prefix) + synthState + "State";
+                sb.append(String.format("        d.put(\"%s.%s\", new %s());\n",
+                                        prefix, synthState, className));
+
+                String body = type.getCodeSnippet();
+                Map<String, String> variables = Generator.getVariables();
+                variables.put("STATE_NAME", className);
+                variables.put("STATE_KEY", synthState);
+                variables.put("BODY", body);
+
+                Generator.writeSrcFile("StateImpl", variables, className);
+            }
+        }
+
+        // write style
+        sb.append(style.write(prefix + '.'));
+
+        String fileName = Utils.normalize(prefix) + "Painter";
+        boolean hasCanvas = hasCanvas();
+        if (hasCanvas) {
+            PainterGenerator.writePainter(this, fileName);
+        }
+        // write states ui defaults
+        for (UIState state : backgroundStates) {
+            state.write(sb, prefix, pkg, fileName, "background");
+        }
+        for (UIState state : foregroundStates) {
+            state.write(sb, prefix, pkg, fileName, "foreground");
+        }
+        for (UIState state : borderStates) {
+            state.write(sb, prefix, pkg, fileName, "border");
+        }
+
+        // handle sub regions
+        for (UIRegion subreg : subRegions) {
+            String p = prefix;
+            if (! (subreg instanceof UIIconRegion)) {
+                p = prefix + ":" + Utils.escape(subreg.getKey());
+            }
+            UIComponent c = comp;
+            if (subreg instanceof UIComponent) {
+                c = (UIComponent) subreg;
+            }
+            subreg.write(sb, styleBuffer, c, p, pkg);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIState.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.Iterator;
+import java.util.List;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+
+class UIState {
+    @XmlAttribute private String stateKeys;
+    public String getStateKeys() { return stateKeys; }
+
+    /** Indicates whether to invert the meaning of the 9-square stretching insets */
+    @XmlAttribute private boolean inverted;
+
+    /** A cached string representing the list of stateKeys deliminated with "+" */
+    private String cachedName = null;
+
+    @XmlElement private Canvas canvas;
+    public Canvas getCanvas() { return canvas; }
+
+    @XmlElement private UIStyle style;
+    public UIStyle getStyle() { return style; }
+
+    public boolean hasCanvas() {
+        return ! canvas.isBlank();
+    }
+
+    public static List<String> stringToKeys(String keysString) {
+        return Arrays.asList(keysString.split("\\+"));
+    }
+
+    public String getName() {
+        if (cachedName == null) {
+            StringBuilder buf = new StringBuilder();
+            List<String> keys = stringToKeys(stateKeys);
+            Collections.sort(keys);
+            for (Iterator<String> iter = keys.iterator(); iter.hasNext();) {
+                buf.append(iter.next());
+                if (iter.hasNext()) {
+                    buf.append('+');
+                }
+            }
+            cachedName = buf.toString();
+        }
+        return cachedName;
+    }
+
+    public void write(StringBuilder sb, String prefix, String pkg, String fileNamePrefix, String painterPrefix) {
+        String statePrefix = prefix + "[" + getName() + "]";
+        // write state style
+        sb.append(style.write(statePrefix + '.'));
+        // write painter
+        if (hasCanvas()) {
+            writeLazyPainter(sb, statePrefix, pkg, fileNamePrefix, painterPrefix);
+        }
+    }
+
+    private void writeLazyPainter(StringBuilder sb, String statePrefix, String packageNamePrefix, String fileNamePrefix, String painterPrefix) {
+        String cacheModeString = "AbstractRegionPainter.PaintContext.CacheMode." + style.getCacheMode();
+        String stateConstant = Utils.statesToConstantName(painterPrefix + "_" + stateKeys);
+        sb.append(String.format(
+                "        d.put(\"%s.%sPainter\", new LazyPainter(\"%s.%s\", %s.%s, %s, %s, %b, %s, %s, %s));\n",
+                statePrefix, painterPrefix, packageNamePrefix, fileNamePrefix,
+                fileNamePrefix, stateConstant, canvas.getStretchingInsets().write(false),
+                canvas.getSize().write(false), inverted, cacheModeString,
+                Utils.formatDouble(style.getMaxHozCachedImgScaling()),
+                Utils.formatDouble(style.getMaxVertCachedImgScaling())));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/make/tools/src/build/tools/generatenimbus/UIStateType.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2002, 2007, 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 build.tools.generatenimbus;
+
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlElement;
+
+class UIStateType {
+    @XmlAttribute private String key;
+    public String getKey() { return key; }
+
+    @XmlElement private String codeSnippet;
+    public String getCodeSnippet() { return codeSnippet; }
+}
--- a/make/tools/src/build/tools/generatenimbus/UIStyle.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/make/tools/src/build/tools/generatenimbus/UIStyle.java	Mon Nov 05 10:33:18 2012 -0500
@@ -26,15 +26,9 @@
 package build.tools.generatenimbus;
 
 import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.Iterator;
 import java.util.List;
-import java.util.Map;
-import javax.xml.bind.annotation.XmlAttribute;
 import javax.xml.bind.annotation.XmlElement;
 import javax.xml.bind.annotation.XmlElementWrapper;
-import javax.xml.bind.annotation.XmlElements;
 
 
 class UIStyle {
@@ -115,285 +109,3 @@
         return sb.toString();
     }
 }
-
-class UIRegion {
-    @XmlAttribute protected String name;
-    @XmlAttribute protected String key;
-    @XmlAttribute private boolean opaque = false;
-
-    @XmlElement private Insets contentMargins = new Insets(0, 0, 0, 0);
-
-    @XmlElement(name="state")
-    @XmlElementWrapper(name="backgroundStates")
-    protected List<UIState> backgroundStates = new ArrayList<UIState>();
-    public List<UIState> getBackgroundStates() { return backgroundStates; }
-
-    @XmlElement(name="state")
-    @XmlElementWrapper(name="foregroundStates")
-    protected List<UIState> foregroundStates = new ArrayList<UIState>();
-    public List<UIState> getForegroundStates() { return foregroundStates; }
-
-    @XmlElement(name="state")
-    @XmlElementWrapper(name="borderStates")
-    protected List<UIState> borderStates = new ArrayList<UIState>();
-    public List<UIState> getBorderStates() { return borderStates; }
-
-    @XmlElement private UIStyle style = new UIStyle();
-
-    @XmlElements({
-        @XmlElement(name = "region", type = UIRegion.class),
-        @XmlElement(name = "uiComponent", type = UIComponent.class),
-        @XmlElement(name = "uiIconRegion", type = UIIconRegion.class)
-    })
-    @XmlElementWrapper(name="regions")
-    private List<UIRegion> subRegions = new ArrayList<UIRegion>();
-    public List<UIRegion> getSubRegions() { return subRegions; }
-
-    protected void initStyles(UIStyle parentStyle) {
-        style.setParentStyle(parentStyle);
-        for (UIState state: backgroundStates) {
-            state.getStyle().setParentStyle(this.style);
-        }
-        for (UIState state: foregroundStates) {
-            state.getStyle().setParentStyle(this.style);
-        }
-        for (UIState state: borderStates) {
-            state.getStyle().setParentStyle(this.style);
-        }
-        for (UIRegion region: subRegions) {
-            region.initStyles(this.style);
-        }
-    }
-
-    public String getKey() {
-        return key == null || "".equals(key) ? name : key;
-    }
-
-    private boolean hasCanvas() {
-        for (UIState s : backgroundStates) {
-            if (s.hasCanvas()) return true;
-        }
-        for (UIState s : borderStates) {
-            if (s.hasCanvas()) return true;
-        }
-        for (UIState s : foregroundStates) {
-            if (s.hasCanvas()) return true;
-        }
-        for (UIRegion r: subRegions) {
-            if (r.hasCanvas()) return true;
-        }
-        return false;
-    }
-
-    public void write(StringBuilder sb, StringBuilder styleBuffer,
-                      UIComponent comp, String prefix, String pkg) {
-        // write content margins
-        sb.append(String.format("        d.put(\"%s.contentMargins\", %s);\n",
-                                prefix, contentMargins.write(true)));
-        // write opaque if true
-        if (opaque) {
-            sb.append(String.format("        d.put(\"%s.opaque\", Boolean.TRUE);\n", prefix));
-        }
-
-        // register component with LAF
-        String regionCode = "Region." + Utils.regionNameToCaps(name);
-        styleBuffer.append(String.format("        register(%s, \"%s\");\n",
-                                         regionCode, prefix));
-
-        //write the State, if necessary
-        StringBuffer regString = new StringBuffer();
-        List<UIStateType> types = comp.getStateTypes();
-        if (types != null && types.size() > 0) {
-            for (UIStateType type : types) {
-                regString.append(type.getKey());
-                regString.append(",");
-            }
-            //remove the last ","
-            regString.deleteCharAt(regString.length() - 1);
-        }
-
-        if (! regString.equals("Enabled,MouseOver,Pressed,Disabled,Focused,Selected,Default") && types.size() > 0) {
-            //there were either custom states, or the normal states were in a custom order
-            //so go ahead and write out prefix.State
-            sb.append(String.format("        d.put(\"%s.States\", \"%s\");\n",
-                                    prefix, regString));
-        }
-
-        // write out any custom states, if necessary
-        for (UIStateType type : types) {
-            String synthState = type.getKey();
-            if (! "Enabled".equals(synthState) &&
-                ! "MouseOver".equals(synthState) &&
-                ! "Pressed".equals(synthState) &&
-                ! "Disabled".equals(synthState) &&
-                ! "Focused".equals(synthState) &&
-                ! "Selected".equals(synthState) &&
-                ! "Default".equals(synthState)) {
-
-                //what we have here, gentlemen, is a bona-fide custom state.
-                //if the type is not one of the standard types, then construct a name for
-                //the new type, and write out a new subclass of State.
-                String className = Utils.normalize(prefix) + synthState + "State";
-                sb.append(String.format("        d.put(\"%s.%s\", new %s());\n",
-                                        prefix, synthState, className));
-
-                String body = type.getCodeSnippet();
-                Map<String, String> variables = Generator.getVariables();
-                variables.put("STATE_NAME", className);
-                variables.put("STATE_KEY", synthState);
-                variables.put("BODY", body);
-
-                Generator.writeSrcFile("StateImpl", variables, className);
-            }
-        }
-
-        // write style
-        sb.append(style.write(prefix + '.'));
-
-        String fileName = Utils.normalize(prefix) + "Painter";
-        boolean hasCanvas = hasCanvas();
-        if (hasCanvas) {
-            PainterGenerator.writePainter(this, fileName);
-        }
-        // write states ui defaults
-        for (UIState state : backgroundStates) {
-            state.write(sb, prefix, pkg, fileName, "background");
-        }
-        for (UIState state : foregroundStates) {
-            state.write(sb, prefix, pkg, fileName, "foreground");
-        }
-        for (UIState state : borderStates) {
-            state.write(sb, prefix, pkg, fileName, "border");
-        }
-
-        // handle sub regions
-        for (UIRegion subreg : subRegions) {
-            String p = prefix;
-            if (! (subreg instanceof UIIconRegion)) {
-                p = prefix + ":" + Utils.escape(subreg.getKey());
-            }
-            UIComponent c = comp;
-            if (subreg instanceof UIComponent) {
-                c = (UIComponent) subreg;
-            }
-            subreg.write(sb, styleBuffer, c, p, pkg);
-        }
-    }
-}
-
-class UIIconRegion extends UIRegion {
-    @XmlAttribute private String basicKey;
-
-    @Override public void write(StringBuilder sb, StringBuilder styleBuffer, UIComponent comp, String prefix, String pkg) {
-        Dimension size = null;
-        String fileNamePrefix = Utils.normalize(prefix) + "Painter";
-        // write states ui defaults
-        for (UIState state : backgroundStates) {
-            Canvas canvas = state.getCanvas();
-            if (!canvas.isBlank()) {
-                state.write(sb, prefix, pkg, fileNamePrefix, getKey());
-                size = canvas.getSize();
-            }
-        }
-
-        if (size != null) {
-            // Put SynthIconImpl wrapper in UiDefaults
-            String k = (basicKey == null ? prefix + "." + getKey() : basicKey);
-            sb.append(String.format(
-                    "        d.put(\"%s\", new NimbusIcon(\"%s\", \"%sPainter\", %d, %d));\n",
-                    k, prefix, getKey(), size.width, size.height));
-        }
-    }
-}
-
-class UIComponent extends UIRegion {
-    @XmlAttribute private String componentName;
-
-    @XmlElement(name="stateType")
-    @XmlElementWrapper(name="stateTypes")
-    private List<UIStateType> stateTypes = new ArrayList<UIStateType>();
-    public List<UIStateType> getStateTypes() { return stateTypes; }
-
-    @Override public String getKey() {
-        if (key == null || "".equals(key)) {
-            if (componentName == null || "".equals(componentName)) {
-                return name;
-            } else {
-                return "\"" + componentName + "\"";
-            }
-        } else {
-            return key;
-        }
-    }
-}
-
-class UIState {
-    @XmlAttribute private String stateKeys;
-    public String getStateKeys() { return stateKeys; }
-
-    /** Indicates whether to invert the meaning of the 9-square stretching insets */
-    @XmlAttribute private boolean inverted;
-
-    /** A cached string representing the list of stateKeys deliminated with "+" */
-    private String cachedName = null;
-
-    @XmlElement private Canvas canvas;
-    public Canvas getCanvas() { return canvas; }
-
-    @XmlElement private UIStyle style;
-    public UIStyle getStyle() { return style; }
-
-    public boolean hasCanvas() {
-        return ! canvas.isBlank();
-    }
-
-    public static List<String> stringToKeys(String keysString) {
-        return Arrays.asList(keysString.split("\\+"));
-    }
-
-    public String getName() {
-        if (cachedName == null) {
-            StringBuilder buf = new StringBuilder();
-            List<String> keys = stringToKeys(stateKeys);
-            Collections.sort(keys);
-            for (Iterator<String> iter = keys.iterator(); iter.hasNext();) {
-                buf.append(iter.next());
-                if (iter.hasNext()) {
-                    buf.append('+');
-                }
-            }
-            cachedName = buf.toString();
-        }
-        return cachedName;
-    }
-
-    public void write(StringBuilder sb, String prefix, String pkg, String fileNamePrefix, String painterPrefix) {
-        String statePrefix = prefix + "[" + getName() + "]";
-        // write state style
-        sb.append(style.write(statePrefix + '.'));
-        // write painter
-        if (hasCanvas()) {
-            writeLazyPainter(sb, statePrefix, pkg, fileNamePrefix, painterPrefix);
-        }
-    }
-
-    private void writeLazyPainter(StringBuilder sb, String statePrefix, String packageNamePrefix, String fileNamePrefix, String painterPrefix) {
-        String cacheModeString = "AbstractRegionPainter.PaintContext.CacheMode." + style.getCacheMode();
-        String stateConstant = Utils.statesToConstantName(painterPrefix + "_" + stateKeys);
-        sb.append(String.format(
-                "        d.put(\"%s.%sPainter\", new LazyPainter(\"%s.%s\", %s.%s, %s, %s, %b, %s, %s, %s));\n",
-                statePrefix, painterPrefix, packageNamePrefix, fileNamePrefix,
-                fileNamePrefix, stateConstant, canvas.getStretchingInsets().write(false),
-                canvas.getSize().write(false), inverted, cacheModeString,
-                Utils.formatDouble(style.getMaxHozCachedImgScaling()),
-                Utils.formatDouble(style.getMaxVertCachedImgScaling())));
-    }
-}
-
-class UIStateType {
-    @XmlAttribute private String key;
-    public String getKey() { return key; }
-
-    @XmlElement private String codeSnippet;
-    public String getCodeSnippet() { return codeSnippet; }
-}
--- a/makefiles/CompileJavaClasses.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/CompileJavaClasses.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -312,7 +312,8 @@
 JDK_BASE_HEADER_CLASSES:=java.lang.Integer \
 			 java.lang.Long \
 			 java.net.SocketOptions \
-			 sun.nio.ch.IOStatus
+			 sun.nio.ch.IOStatus \
+			 java.io.FileSystem
 
 JDK_BASE_HEADER_JAVA_FILES:=$(patsubst %,$(JDK_TOPDIR)/src/share/classes/%.java,\
 				$(subst .,/,$(JDK_BASE_HEADER_CLASSES)))
--- a/makefiles/CompileNativeLibraries.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/CompileNativeLibraries.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -1540,96 +1540,6 @@
 
 ##########################################################################################
 
-ifndef OPENJDK
-ifneq ($(OPENJDK_TARGET_OS), macosx)
-
-LIBJDBCODBC_DIR   :=$(JDK_OUTPUTDIR)/objs/libjdbcodbc
-LIBJDBCODBC_NAME  :=$(LIBRARY_PREFIX)JdbcOdbc$(SHARED_LIBRARY_SUFFIX)
-LIBJDBCODBC_CFLAGS:=
-LIBJDBCODBC_LIBS   :=
-LIBJDBCODBC_LDFLAGS:=
-
-ifeq ($(OPENJDK_TARGET_OS), windows)
-	LIBJDBCODBC_LDFLAGS:=$(LDFLAGS_JDKLIB)
-	LIBJDBCODBC_LIBS += odbc32.lib odbccp32.lib $(WIN_JAVA_LIB) advapi32.lib
-else
-	LIBJDBCODBC_CFLAGS:=-DUNIX
-
-#
-# This mimics "current" build system exactly. Link against fake -lodbcinst -lodbc
-#   but...those are linked with the -soname, causing the dependency to be dropped on linux (gnu ld)
-#   but kept with other linker (solaris)
-#
-# IMO very weird behaviour...very weird
-#
-	LIBJDBCODBC_LDFLAGS:=$(patsubst defs,nodefs,$(LDFLAGS_JDKLIB)) \
-				      -Xlinker -z -Xlinker nodefs
-	LIBJDBCODBC_LIBS += -L$(LIBJDBCODBC_DIR) -lodbcinst -lodbc
-	LIBJDBCODBC_SONAME:=$(call SET_SHARED_LIBRARY_NAME,$(LIBJDBCODBC_NAME))
-endif
-
-$(eval $(call SetupNativeCompilation,BUILD_LIBJDBCODBC,\
-		LIBRARY:=JdbcOdbc,\
-                OUTPUT_DIR:=$(INSTALL_LIBRARIES_HERE),\
-		SRC:=$(JDK_TOPDIR)/src/closed/share/classes/sun/jdbc/odbc,\
-		EXCLUDE_FILES:=dummyodbc.c,\
-		LANG:=C,\
-		OPTIMIZATION:=LOW, \
-		CFLAGS:=$(LIBJDBCODBC_CFLAGS) $(CFLAGS_JDKLIB) \
-			$(SHARED_LIBRARY_FLAGS),\
-		LDFLAGS:=$(LIBJDBCODBC_LDFLAGS) \
-			 $(call SET_SHARED_LIBRARY_ORIGIN) $(LIBJDBCODBC_LIBS),\
-		LDFLAGS_SUFFIX:=$(LDFLAGS_JDKLIB_SUFFIX) $(LIBJDBCODBC_SONAME),\
-		VERSIONINFO_RESOURCE:=$(JDK_TOPDIR)/src/windows/resource/version.rc,\
-		RC_FLAGS:=$(RC_FLAGS)\
-			  /D "JDK_FNAME=JdbcOdbc.dll" \
-			  /D "JDK_INTERNAL_NAME=JdbcOdbc" \
-			  /D "JDK_FTYPE=0x2L",\
-		OBJECT_DIR:=$(LIBJDBCODBC_DIR),\
-		DEBUG_SYMBOLS:=$(WINDOWS_ONLY)))
-
-$(BUILD_LIBJDBCODBC) : $(BUILD_LIBJAVA)
-
-BUILD_LIBRARIES += $(BUILD_LIBJDBCODBC)
-
-ifneq ($(OPENJDK_TARGET_OS), windows)
-
-$(eval $(call SetupNativeCompilation,BUILD_FAKEODBCINST,\
-		LIBRARY:=odbcinst,\
-                OUTPUT_DIR:=$(LIBJDBCODBC_DIR),\
-		SRC:=$(JDK_OUTPUTDIR)/gensrc_c/libjdbcodbc,\
-		INCLUDE_FILES:=dummyodbc1.c,\
-		LANG:=C,\
-		OPTIMIZATION:=LOW, \
-		CFLAGS:=$(CFLAGS_JDKLIB),\
-		LDFLAGS:=$(LDFLAGS_JDKLIB) $(call SET_SHARED_LIBRARY_ORIGIN) $(LIBJDBCODBC_LDFLAGS),\
-		LDFLAGS_SUFFIX:=$(LDFLAGS_JDKLIB_SUFFIX) $(LIBJDBCODBC_SONAME),\
-		OBJECT_DIR:=$(LIBJDBCODBC_DIR)))
-
-$(eval $(call SetupNativeCompilation,BUILD_FAKEODBC,\
-		LIBRARY:=odbc,\
-                OUTPUT_DIR:=$(LIBJDBCODBC_DIR),\
-		SRC:=$(JDK_OUTPUTDIR)/gensrc_c/libjdbcodbc,\
-		INCLUDE_FILES:=dummyodbc2.c,\
-		LANG:=C,\
-		OPTIMIZATION:=LOW, \
-		CFLAGS:=$(LIBJDBCODBC_CFLAGS) $(CFLAGS_JDKLIB),\
-		LDFLAGS:=$(LDFLAGS_JDKLIB) $(call SET_SHARED_LIBRARY_ORIGIN) $(LIBJDBCODBC_LDFLAGS),\
-		LDFLAGS_SUFFIX:=$(LDFLAGS_JDKLIB_SUFFIX) $(LIBJDBCODBC_SONAME),\
-		OBJECT_DIR:=$(LIBJDBCODBC_DIR)))
-
-$(BUILD_FAKEODBCINST) $(BUILD_FAKEODBC) : \
-  $(BUILD_LIBJAVA)
-
-$(BUILD_LIBJDBCODBC) : $(BUILD_FAKEODBCINST) $(BUILD_FAKEODBC)
-
-endif
-
-endif
-endif
-
-##########################################################################################
-
 LIBINSTRUMENT_SRC   :=$(JDK_TOPDIR)/src/share/instrument \
                       $(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/native/java/io \
                       $(JDK_TOPDIR)/src/$(OPENJDK_TARGET_OS_API_DIR)/instrument
--- a/makefiles/CopyIntoClasses.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/CopyIntoClasses.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -189,12 +189,6 @@
 endif
 
 ifndef OPENJDK
-ifneq ($(OPENJDK_TARGET_OS), macosx)
-    ALL_META-INF_DIRS += $(JDK_TOPDIR)/src/closed/share/classes/sun/jdbc/odbc/META-INF
-endif
-endif
-
-ifndef OPENJDK
     ALL_META-INF_DIRS += $(JDK_TOPDIR)/src/closed/share/classes/sun/java2d/cmm/kcms/META-INF
 endif
 
--- a/makefiles/CreateJars.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/CreateJars.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -74,10 +74,46 @@
 
 ##########################################################################################
 
-LOCALEDATA_INCLUDE_LOCALES := ar hi iw ja ko th vi zh
+LOCALEDATA_INCLUDE_LOCALES := ar be bg ca cs da de el es et fi fr ga hi hr hu in is it \
+                              iw ja ko lt lv mk ms mt nl no pl pt ro ru sk sl sq sr sv \
+                              th tr uk vi zh
+
 LOCALEDATA_INCLUDES := $(addprefix sun/text/resources/,$(LOCALEDATA_INCLUDE_LOCALES)) \
 		       $(addprefix sun/util/resources/,$(LOCALEDATA_INCLUDE_LOCALES))
 
+# For non-US English locale data
+
+LOCALEDATA_INCLUDES += \
+                sun/text/resources/en/FormatData_en_AU.class \
+                sun/text/resources/en/FormatData_en_CA.class \
+                sun/text/resources/en/FormatData_en_GB.class \
+                sun/text/resources/en/FormatData_en_IE.class \
+                sun/text/resources/en/FormatData_en_IN.class \
+                sun/text/resources/en/FormatData_en_MT.class \
+                sun/text/resources/en/FormatData_en_NZ.class \
+                sun/text/resources/en/FormatData_en_PH.class \
+                sun/text/resources/en/FormatData_en_SG.class \
+                sun/text/resources/en/FormatData_en_ZA.class \
+                sun/util/resources/en/CalendarData_en_GB.class \
+                sun/util/resources/en/CalendarData_en_IE.class \
+                sun/util/resources/en/CalendarData_en_MT.class \
+                sun/util/resources/en/CurrencyNames_en_AU.class \
+                sun/util/resources/en/CurrencyNames_en_CA.class \
+                sun/util/resources/en/CurrencyNames_en_GB.class \
+                sun/util/resources/en/CurrencyNames_en_IE.class \
+                sun/util/resources/en/CurrencyNames_en_IN.class \
+                sun/util/resources/en/CurrencyNames_en_MT.class \
+                sun/util/resources/en/CurrencyNames_en_NZ.class \
+                sun/util/resources/en/CurrencyNames_en_PH.class \
+                sun/util/resources/en/CurrencyNames_en_SG.class \
+                sun/util/resources/en/CurrencyNames_en_ZA.class \
+                sun/util/resources/en/LocaleNames_en_MT.class \
+                sun/util/resources/en/LocaleNames_en_PH.class \
+                sun/util/resources/en/LocaleNames_en_SG.class \
+                sun/util/resources/en/TimeZoneNames_en_CA.class \
+                sun/util/resources/en/TimeZoneNames_en_GB.class \
+                sun/util/resources/en/TimeZoneNames_en_IE.class
+
 $(eval $(call SetupArchive,BUILD_LOCALEDATA_JAR,,\
 		SRCS:=$(JDK_OUTPUTDIR)/classes,\
 		SUFFIXES:=.class _dict _th,\
@@ -249,7 +285,6 @@
 ifeq ($(OPENJDK_TARGET_OS), macosx)
         RT_JAR_EXCLUDES += com/sun/nio/sctp \
                            sun/nio/ch/sctp \
-                           sun/jdbc \
                            sun/nio/ch/DevPollArrayWrapper\$$$$Updator.class \
                            sun/nio/ch/DevPollArrayWrapper.class \
                            sun/nio/ch/DevPollSelectorImpl.class \
--- a/makefiles/GensrcLocaleDataMetaInfo.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/GensrcLocaleDataMetaInfo.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -50,26 +50,26 @@
     $(shell $(RM) $(JDK_OUTPUTDIR)/gensrc_localedatametainfo/sun/util/locale/provider/LocaleDataMetaInfo.java)
 endif
 
-# The non-euro zone locales have to be separated from the euro-zone locales.
-NON_EURO_LOCALES:=ar% hi% iw% ja% ko% th% vi% zh%
+# The US locales
+US_LOCALES:=en en-US
 
 # ja-JP-JP and th-TH-TH need to be manually added, as they don't have any resource files.
-ALL_NON_EURO_LOCALES:=ja-JP-JP th-TH-TH
+ALL_NON_US_LOCALES:=ja-JP-JP th-TH-TH
 
 SED_ARGS:=-e 's|$(HASH)warn This file is preprocessed before being compiled|// -- This file was mechanically generated: Do not edit! -- //|g'
 
 # This macro creates a sed expression that substitues for example:
-# #FormatData_EuroLocales# with: be be_BY bg bg_BG ca ca_ES... and some more.
+# #FormatData_USLocales# with: en and/or en_US.
 define CaptureLocale
     $1_LOCALES := $$(subst _,-,$$(filter-out $1,$$(subst $1_,,$$(filter $1_%,$(LOCALE_RESOURCES)))))
-    $1_EURO_LOCALES := $$(filter-out $(NON_EURO_LOCALES),$$($1_LOCALES))
-    $1_NON_EURO_LOCALES := $$(filter $(NON_EURO_LOCALES),$$($1_LOCALES))
+    $1_US_LOCALES := $$(filter $(US_LOCALES),$$($1_LOCALES))
+    $1_NON_US_LOCALES := $$(filter-out $(US_LOCALES),$$($1_LOCALES))
 
-    ALL_EURO_LOCALES += $$($1_EURO_LOCALES)
-    ALL_NON_EURO_LOCALES += $$($1_NON_EURO_LOCALES)
+    ALL_US_LOCALES += $$($1_US_LOCALES)
+    ALL_NON_US_LOCALES += $$($1_NON_US_LOCALES)
 
-    SED_ARGS+= -e 's/$$(HASH)$1_EuroLocales$$(HASH)/ $$($1_EURO_LOCALES)/g'
-    SED_ARGS+= -e 's/$$(HASH)$1_NonEuroLocales$$(HASH)/ $$($1_NON_EURO_LOCALES)/g'
+    SED_ARGS+= -e 's/$$(HASH)$1_USLocales$$(HASH)/ $$($1_US_LOCALES)/g'
+    SED_ARGS+= -e 's/$$(HASH)$1_NonUSLocales$$(HASH)/ $$($1_NON_US_LOCALES)/g'
 endef
 
 #sun.text.resources.FormatData
@@ -90,8 +90,8 @@
 #sun.util.resources.CalendarData
 $(eval $(call CaptureLocale,CalendarData))
 
-SED_ARGS+= -e 's/$(HASH)AvailableLocales_EuroLocales$(HASH)/$(sort $(ALL_EURO_LOCALES))/g'
-SED_ARGS+= -e 's/$(HASH)AvailableLocales_NonEuroLocales$(HASH)/$(sort $(ALL_NON_EURO_LOCALES))/g'
+SED_ARGS+= -e 's/$(HASH)AvailableLocales_USLocales$(HASH)/$(sort $(ALL_US_LOCALES))/g'
+SED_ARGS+= -e 's/$(HASH)AvailableLocales_NonUSLocales$(HASH)/$(sort $(ALL_NON_US_LOCALES))/g'
 
 $(JDK_OUTPUTDIR)/gensrc_localedatametainfo/sun/util/locale/provider/LocaleDataMetaInfo.java: \
 		$(JDK_TOPDIR)/src/share/classes/sun/util/locale/provider/LocaleDataMetaInfo-XLocales.java.template
--- a/makefiles/GensrcMisc.gmk	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/GensrcMisc.gmk	Mon Nov 05 10:33:18 2012 -0500
@@ -77,32 +77,6 @@
 
 ##########################################################################################
 
-ifndef OPENJDK
-ifneq ($(OPENJDK_TARGET_OS), windows)
-ifneq ($(OPENJDK_TARGET_OS), macosx)
-    # These file(s) are needed for building fake .so libs on !windows for jdbcodbc
-
-    $(JDK_OUTPUTDIR)/gensrc_c/libjdbcodbc/dummyodbc1.c : 
-	$(MKDIR) -p $(@D)
-	$(RM) $@
-	$(ECHO) Creating $@
-	$(PRINTF) "void dummyOdbc(void){}\n" > $@
-	$(ECHO) Created $@
-
-    $(JDK_OUTPUTDIR)/gensrc_c/libjdbcodbc/dummyodbc2.c : 
-	$(MKDIR) -p $(@D)
-	$(RM) $@
-	$(ECHO) Creating $@
-	$(PRINTF) "void dummyOdbc(void){}\n" > $@
-	$(ECHO) Created $@
-
-    GENSRC_MISC += $(JDK_OUTPUTDIR)/gensrc_c/libjdbcodbc/dummyodbc1.c $(JDK_OUTPUTDIR)/gensrc_c/libjdbcodbc/dummyodbc2.c
-endif
-endif
-endif
-
-##########################################################################################
-
 GENSRC_MISC += $(JDK_OUTPUTDIR)/gensrc_misc/sun/nio/ch/SocketOptionRegistry.java
 
 GENSRC_SOR_SRC := $(JDK_TOPDIR)/src/share/native/sun/nio/ch
--- a/makefiles/mapfiles/libjava/mapfile-vers	Mon Nov 05 10:30:49 2012 -0500
+++ b/makefiles/mapfiles/libjava/mapfile-vers	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 #
-# Copyright (c) 1997, 2009, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 1997, 2012, 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
@@ -87,7 +87,6 @@
 		Java_java_io_FileOutputStream_open;
 		Java_java_io_FileOutputStream_write;
 		Java_java_io_FileOutputStream_writeBytes;
-		Java_java_io_FileSystem_getFileSystem;
 		Java_java_io_ObjectInputStream_bytesToDoubles;
 		Java_java_io_ObjectInputStream_bytesToFloats;
 		Java_java_io_ObjectOutputStream_doublesToBytes;
--- a/src/macosx/classes/com/apple/laf/AquaFileChooserUI.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/classes/com/apple/laf/AquaFileChooserUI.java	Mon Nov 05 10:33:18 2012 -0500
@@ -379,6 +379,19 @@
                         }
                     }
                     updateButtonState(getFileChooser());
+                } else if (prop.equals(JFileChooser.SELECTED_FILES_CHANGED_PROPERTY)) {
+                    JFileChooser fileChooser = getFileChooser();
+                    if (!fileChooser.isDirectorySelectionEnabled()) {
+                        final File[] files = (File[]) e.getNewValue();
+                        if (files != null) {
+                            for (int selectedRow : fFileList.getSelectedRows()) {
+                                File file = (File) fFileList.getValueAt(selectedRow, 0);
+                                if (fileChooser.isTraversable(file)) {
+                                    fFileList.removeSelectedIndex(selectedRow);
+                                }
+                            }
+                        }
+                    }
                 } else if (prop.equals(JFileChooser.DIRECTORY_CHANGED_PROPERTY)) {
                     fFileList.clearSelection();
                     final File currentDirectory = getFileChooser().getCurrentDirectory();
--- a/src/macosx/classes/sun/awt/CGraphicsDevice.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/classes/sun/awt/CGraphicsDevice.java	Mon Nov 05 10:33:18 2012 -0500
@@ -33,9 +33,7 @@
 
 import sun.java2d.opengl.CGLGraphicsConfig;
 
-import sun.awt.FullScreenCapable;
-
-public class CGraphicsDevice extends GraphicsDevice {
+public final class CGraphicsDevice extends GraphicsDevice {
 
     // CoreGraphics display ID
     private final int displayID;
@@ -108,11 +106,6 @@
         return nativeGetYResolution(displayID);
     }
 
-    public int getScreenResolution() {
-        // TODO: report non-72 value when HiDPI is turned on
-        return 72;
-    }
-
     private static native double nativeGetXResolution(int displayID);
     private static native double nativeGetYResolution(int displayID);
 
@@ -194,6 +187,9 @@
 
     @Override
     public void setDisplayMode(DisplayMode dm) {
+        if (dm == null) {
+            throw new IllegalArgumentException("Invalid display mode");
+        }
         nativeSetDisplayMode(displayID, dm.getWidth(), dm.getHeight(), dm.getBitDepth(), dm.getRefreshRate());
         if (isFullScreenSupported() && getFullScreenWindow() != null) {
             getFullScreenWindow().setSize(dm.getWidth(), dm.getHeight());
--- a/src/macosx/classes/sun/lwawt/macosx/CPlatformWindow.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/classes/sun/lwawt/macosx/CPlatformWindow.java	Mon Nov 05 10:33:18 2012 -0500
@@ -65,7 +65,7 @@
     private static native void nativeDispose(long nsWindowPtr);
     private static native CPlatformWindow nativeGetTopmostPlatformWindowUnderMouse();
 
-    private static native int nativeGetNSWindowDisplayID_AppKitThread(long nsWindowPtr);
+    private static native int nativeGetNSWindowDisplayID(long nsWindowPtr);
 
     // Loger to report issues happened during execution but that do not affect functionality
     private static final PlatformLogger logger = PlatformLogger.getLogger("sun.lwawt.macosx.CPlatformWindow");
@@ -444,7 +444,7 @@
     public GraphicsDevice getGraphicsDevice() {
         GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
         CGraphicsEnvironment cge = (CGraphicsEnvironment)ge;
-        int displayID = nativeGetNSWindowDisplayID_AppKitThread(getNSWindowPtr());
+        int displayID = nativeGetNSWindowDisplayID(getNSWindowPtr());
         GraphicsDevice gd = cge.getScreenDevice(displayID);
         if (gd == null) {
             // this could possibly happen during device removal
--- a/src/macosx/classes/sun/lwawt/macosx/CTrayIcon.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/classes/sun/lwawt/macosx/CTrayIcon.java	Mon Nov 05 10:33:18 2012 -0500
@@ -26,6 +26,7 @@
 package sun.lwawt.macosx;
 
 import sun.awt.SunToolkit;
+import sun.lwawt.macosx.event.NSEvent;
 
 import javax.swing.*;
 import java.awt.*;
@@ -42,6 +43,16 @@
     private JDialog messageDialog;
     private DialogEventHandler handler;
 
+    // In order to construct MouseEvent object, we need to specify a
+    // Component target. Because TrayIcon isn't Component's subclass,
+    // we use this dummy frame instead
+    private final Frame dummyFrame;
+
+    // A bitmask that indicates what mouse buttons produce MOUSE_CLICKED events
+    // on MOUSE_RELEASE. Click events are only generated if there were no drag
+    // events between MOUSE_PRESSED and MOUSE_RELEASED for particular button
+    private static int mouseClickButtons = 0;
+
     CTrayIcon(TrayIcon target) {
         super(0, true);
 
@@ -49,6 +60,7 @@
         this.handler = null;
         this.target = target;
         this.popup = target.getPopupMenu();
+        this.dummyFrame = new Frame();
         setPtr(createModel());
 
         //if no one else is creating the peer.
@@ -119,6 +131,8 @@
             disposeMessageDialog();
         }
 
+        dummyFrame.dispose();
+
         LWCToolkit.targetDisposedPeer(target, this);
         target = null;
 
@@ -161,17 +175,78 @@
 
     private native void setNativeImage(final long model, final long nsimage, final boolean autosize);
 
-    //invocation from the AWTTrayIcon.m
-    public void performAction() {
+    private void postEvent(final AWTEvent event) {
         SunToolkit.executeOnEventHandlerThread(target, new Runnable() {
             public void run() {
-                final String cmd = target.getActionCommand();
-                final ActionEvent event = new ActionEvent(target, ActionEvent.ACTION_PERFORMED, cmd);
                 SunToolkit.postEvent(SunToolkit.targetToAppContext(target), event);
             }
         });
     }
 
+    //invocation from the AWTTrayIcon.m
+    private void handleMouseEvent(NSEvent nsEvent) {
+        int buttonNumber = nsEvent.getButtonNumber();
+        final SunToolkit tk = (SunToolkit)Toolkit.getDefaultToolkit();
+        if ((buttonNumber > 2 && !tk.areExtraMouseButtonsEnabled())
+                || buttonNumber > tk.getNumberOfButtons() - 1) {
+            return;
+        }
+
+        int jeventType = NSEvent.nsToJavaEventType(nsEvent.getType());
+
+        int jbuttonNumber = MouseEvent.NOBUTTON;
+        int jclickCount = 0;
+        if (jeventType != MouseEvent.MOUSE_MOVED) {
+            jbuttonNumber = NSEvent.nsToJavaButton(buttonNumber);
+            jclickCount = nsEvent.getClickCount();
+        }
+
+        int jmodifiers = NSEvent.nsToJavaMouseModifiers(buttonNumber,
+                nsEvent.getModifierFlags());
+        boolean isPopupTrigger = NSEvent.isPopupTrigger(jmodifiers);
+
+        int eventButtonMask = (jbuttonNumber > 0)?
+                MouseEvent.getMaskForButton(jbuttonNumber) : 0;
+        long when = System.currentTimeMillis();
+
+        if (jeventType == MouseEvent.MOUSE_PRESSED) {
+            mouseClickButtons |= eventButtonMask;
+        } else if (jeventType == MouseEvent.MOUSE_DRAGGED) {
+            mouseClickButtons = 0;
+        }
+
+        // The MouseEvent's coordinates are relative to screen
+        int absX = nsEvent.getAbsX();
+        int absY = nsEvent.getAbsY();
+
+        MouseEvent mouseEvent = new MouseEvent(dummyFrame, jeventType, when,
+                jmodifiers, absX, absY, absX, absY, jclickCount, isPopupTrigger,
+                jbuttonNumber);
+        mouseEvent.setSource(target);
+        postEvent(mouseEvent);
+
+        // fire ACTION event
+        if (jeventType == MouseEvent.MOUSE_PRESSED && isPopupTrigger) {
+            final String cmd = target.getActionCommand();
+            final ActionEvent event = new ActionEvent(target,
+                    ActionEvent.ACTION_PERFORMED, cmd);
+            postEvent(event);
+        }
+
+        // synthesize CLICKED event
+        if (jeventType == MouseEvent.MOUSE_RELEASED) {
+            if ((mouseClickButtons & eventButtonMask) != 0) {
+                MouseEvent clickEvent = new MouseEvent(dummyFrame,
+                        MouseEvent.MOUSE_CLICKED, when, jmodifiers, absX, absY,
+                        absX, absY, jclickCount, isPopupTrigger, jbuttonNumber);
+                clickEvent.setSource(target);
+                postEvent(clickEvent);
+            }
+
+            mouseClickButtons &= ~eventButtonMask;
+        }
+    }
+
     private native Point2D nativeGetIconLocation(long trayIconModel);
 
     public void displayMessageOnEDT(String caption, String text,
@@ -256,6 +331,9 @@
 
         dialog.setDefaultCloseOperation(JDialog.DO_NOTHING_ON_CLOSE);
         dialog.setModal(false);
+        dialog.setModalExclusionType(Dialog.ModalExclusionType.TOOLKIT_EXCLUDE);
+        dialog.setAlwaysOnTop(true);
+        dialog.setAutoRequestFocus(false);
         dialog.setResizable(false);
         dialog.setContentPane(op);
 
--- a/src/macosx/classes/sun/lwawt/macosx/LWCToolkit.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/classes/sun/lwawt/macosx/LWCToolkit.java	Mon Nov 05 10:33:18 2012 -0500
@@ -53,7 +53,7 @@
 /**
  * Mac OS X Cocoa-based AWT Toolkit.
  */
-public class LWCToolkit extends LWToolkit {
+public final class LWCToolkit extends LWToolkit {
     // While it is possible to enumerate all mouse devices
     // and query them for the number of buttons, the code
     // that does it is rather complex. Instead, we opt for
@@ -278,7 +278,6 @@
         return new CMouseInfoPeer();
     }
 
-
     @Override
     protected int getScreenHeight() {
         return GraphicsEnvironment.getLocalGraphicsEnvironment()
@@ -333,8 +332,9 @@
 
     @Override
     public int getScreenResolution() throws HeadlessException {
-        return ((CGraphicsDevice) GraphicsEnvironment
-                .getLocalGraphicsEnvironment().getDefaultScreenDevice()).getScreenResolution();
+        return (int) ((CGraphicsDevice) GraphicsEnvironment
+                .getLocalGraphicsEnvironment().getDefaultScreenDevice())
+                .getXResolution();
     }
 
     @Override
--- a/src/macosx/native/sun/awt/AWTWindow.m	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/native/sun/awt/AWTWindow.m	Mon Nov 05 10:33:18 2012 -0500
@@ -324,6 +324,13 @@
     }
 }
 
++ (NSNumber *) getNSWindowDisplayID_AppKitThread:(NSWindow *)window {
+    AWT_ASSERT_APPKIT_THREAD;
+    NSScreen *screen = [window screen];
+    NSDictionary *deviceDescription = [screen deviceDescription];
+    return [deviceDescription objectForKey:@"NSScreenNumber"];
+}
+
 - (void) dealloc {
 AWT_ASSERT_APPKIT_THREAD;
 
@@ -1113,19 +1120,22 @@
  * Signature: (J)I
  */
 JNIEXPORT jint JNICALL
-Java_sun_lwawt_macosx_CPlatformWindow_nativeGetNSWindowDisplayID_1AppKitThread
+Java_sun_lwawt_macosx_CPlatformWindow_nativeGetNSWindowDisplayID
 (JNIEnv *env, jclass clazz, jlong windowPtr)
 {
-    jint ret; // CGDirectDisplayID
+    __block jint ret; // CGDirectDisplayID
 
 JNF_COCOA_ENTER(env);
-AWT_ASSERT_APPKIT_THREAD;
 
     NSWindow *window = OBJC(windowPtr);
-    NSScreen *screen = [window screen];
-    NSDictionary *deviceDescription = [screen deviceDescription];
-    NSNumber *displayID = [deviceDescription objectForKey:@"NSScreenNumber"];
-    ret = (jint)[displayID intValue];
+
+    if ([NSThread isMainThread]) {
+        ret = (jint)[[AWTWindow getNSWindowDisplayID_AppKitThread: window] intValue];
+    } else {
+        [JNFRunLoop performOnMainThreadWaiting:YES withBlock:^(){
+            ret = (jint)[[AWTWindow getNSWindowDisplayID_AppKitThread: window] intValue];
+        }];
+    }
 
 JNF_COCOA_EXIT(env);
 
--- a/src/macosx/native/sun/awt/CTrayIcon.h	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/native/sun/awt/CTrayIcon.h	Mon Nov 05 10:33:18 2012 -0500
@@ -53,6 +53,7 @@
 - (jobject) peer;
 - (void) setImage:(NSImage *) imagePtr sizing:(BOOL)autosize;
 - (NSPoint) getLocationOnScreen;
+- (void) deliverJavaMouseEvent:(NSEvent*) event;
 
 @end //AWTTrayIcon
 
@@ -68,6 +69,7 @@
 -(id)initWithTrayIcon:(AWTTrayIcon *)theTrayIcon;
 -(void)setHighlighted:(BOOL)aFlag;
 -(void)setImage:(NSImage*)anImage;
+-(void)setTrayIcon:(AWTTrayIcon*)theTrayIcon;
 
 @end //AWTTrayIconView
 
--- a/src/macosx/native/sun/awt/CTrayIcon.m	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/macosx/native/sun/awt/CTrayIcon.m	Mon Nov 05 10:33:18 2012 -0500
@@ -29,6 +29,7 @@
 #import "CTrayIcon.h"
 #import "ThreadUtilities.h"
 #include "GeomUtilities.h"
+#import "LWCToolkit.h"
 
 #define kImageInset 4.0
 
@@ -76,8 +77,9 @@
     // Its a bad idea to force the item to release our view by setting
     // the item's view to nil: it can lead to a crash in some scenarios.
     // The item will release the view later on, so just set the view's image
-    // to nil since we are done with it.
+    // and tray icon to nil since we are done with it.
     [view setImage: nil];
+    [view setTrayIcon: nil];
     [view release];
 
     [theItem release];
@@ -115,6 +117,45 @@
     return [[view window] convertBaseToScreen: NSZeroPoint];
 }
 
+-(void) deliverJavaMouseEvent: (NSEvent *) event {
+    [AWTToolkit eventCountPlusPlus];
+
+    JNIEnv *env = [ThreadUtilities getJNIEnv];
+
+    NSPoint eventLocation = [event locationInWindow];
+    NSPoint localPoint = [view convertPoint: eventLocation fromView: nil];
+    localPoint.y = [view bounds].size.height - localPoint.y;
+
+    NSPoint absP = [NSEvent mouseLocation];
+    NSEventType type = [event type];
+
+    NSRect screenRect = [[NSScreen mainScreen] frame];
+    absP.y = screenRect.size.height - absP.y;
+    jint clickCount;
+
+    clickCount = [event clickCount];
+
+    static JNF_CLASS_CACHE(jc_NSEvent, "sun/lwawt/macosx/event/NSEvent");
+    static JNF_CTOR_CACHE(jctor_NSEvent, jc_NSEvent, "(IIIIIIIIDD)V");
+    jobject jEvent = JNFNewObject(env, jctor_NSEvent,
+                                  [event type],
+                                  [event modifierFlags],
+                                  clickCount,
+                                  [event buttonNumber],
+                                  (jint)localPoint.x, (jint)localPoint.y,
+                                  (jint)absP.x, (jint)absP.y,
+                                  [event deltaY],
+                                  [event deltaX]);
+    if (jEvent == nil) {
+        // Unable to create event by some reason.
+        return;
+    }
+
+    static JNF_CLASS_CACHE(jc_TrayIcon, "sun/lwawt/macosx/CTrayIcon");
+    static JNF_MEMBER_CACHE(jm_handleMouseEvent, jc_TrayIcon, "handleMouseEvent", "(Lsun/lwawt/macosx/event/NSEvent;)V");
+    JNFCallVoidMethod(env, peer, jm_handleMouseEvent, jEvent);
+}
+
 @end //AWTTrayIcon
 //================================================
 
@@ -123,7 +164,7 @@
 -(id)initWithTrayIcon:(AWTTrayIcon *)theTrayIcon {
     self = [super initWithFrame:NSMakeRect(0, 0, 1, 1)];
 
-    trayIcon = theTrayIcon;
+    [self setTrayIcon: theTrayIcon];
     isHighlighted = NO;
     image = nil;
 
@@ -153,6 +194,10 @@
     }
 }
 
+-(void)setTrayIcon:(AWTTrayIcon*)theTrayIcon {
+    trayIcon = theTrayIcon;
+}
+
 - (void)menuWillOpen:(NSMenu *)menu
 {
     [self setHighlighted:YES];
@@ -191,30 +236,57 @@
      ];
 }
 
-- (void) mouseDown:(NSEvent *)e {
-    //find CTrayIcon.getPopupMenuModel method and call it to get popup menu ptr.
-    JNIEnv *env = [ThreadUtilities getJNIEnv];
-    static JNF_CLASS_CACHE(jc_CTrayIcon, "sun/lwawt/macosx/CTrayIcon");
-    static JNF_MEMBER_CACHE(jm_getPopupMenuModel, jc_CTrayIcon, "getPopupMenuModel", "()J");
-    static JNF_MEMBER_CACHE(jm_performAction, jc_CTrayIcon, "performAction", "()V");
-    jlong res = JNFCallLongMethod(env, trayIcon.peer, jm_getPopupMenuModel);
-    if (res != 0) {
-        CPopupMenu *cmenu = jlong_to_ptr(res);
-        NSMenu* menu = [cmenu menu];
-        [menu setDelegate:self];
-        [trayIcon.theItem popUpStatusItemMenu:menu];
-        [self setNeedsDisplay:YES];
-    } else {
-        JNFCallVoidMethod(env, trayIcon.peer, jm_performAction);
+- (void)mouseDown:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+
+    // don't show the menu on ctrl+click: it triggers ACTION event, like right click
+    if (([event modifierFlags] & NSControlKeyMask) == 0) {
+        //find CTrayIcon.getPopupMenuModel method and call it to get popup menu ptr.
+        JNIEnv *env = [ThreadUtilities getJNIEnv];
+        static JNF_CLASS_CACHE(jc_CTrayIcon, "sun/lwawt/macosx/CTrayIcon");
+        static JNF_MEMBER_CACHE(jm_getPopupMenuModel, jc_CTrayIcon, "getPopupMenuModel", "()J");
+        jlong res = JNFCallLongMethod(env, trayIcon.peer, jm_getPopupMenuModel);
+
+        if (res != 0) {
+            CPopupMenu *cmenu = jlong_to_ptr(res);
+            NSMenu* menu = [cmenu menu];
+            [menu setDelegate:self];
+            [trayIcon.theItem popUpStatusItemMenu:menu];
+            [self setNeedsDisplay:YES];
+        }
     }
 }
 
-- (void) rightMouseDown:(NSEvent *)e {
-    // Call CTrayIcon.performAction() method on right mouse press
-    JNIEnv *env = [ThreadUtilities getJNIEnv];
-    static JNF_CLASS_CACHE(jc_CTrayIcon, "sun/lwawt/macosx/CTrayIcon");
-    static JNF_MEMBER_CACHE(jm_performAction, jc_CTrayIcon, "performAction", "()V");
-    JNFCallVoidMethod(env, trayIcon.peer, jm_performAction);
+- (void) mouseUp:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) mouseDragged:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) rightMouseDown:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) rightMouseUp:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) rightMouseDragged:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) otherMouseDown:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) otherMouseUp:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
+}
+
+- (void) otherMouseDragged:(NSEvent *)event {
+    [trayIcon deliverJavaMouseEvent: event];
 }
 
 
--- a/src/share/classes/com/sun/beans/decoder/DocumentHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/beans/decoder/DocumentHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2012, 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
@@ -37,6 +37,9 @@
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
+import java.security.AccessControlContext;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
 
 import javax.xml.parsers.ParserConfigurationException;
 import javax.xml.parsers.SAXParserFactory;
@@ -46,6 +49,8 @@
 import org.xml.sax.SAXException;
 import org.xml.sax.helpers.DefaultHandler;
 
+import sun.misc.SharedSecrets;
+
 /**
  * The main class to parse JavaBeans XML archive.
  *
@@ -56,11 +61,10 @@
  * @see ElementHandler
  */
 public final class DocumentHandler extends DefaultHandler {
-    private final Map<String, Class<? extends ElementHandler>> handlers = new HashMap<String, Class<? extends ElementHandler>>();
-
-    private final Map<String, Object> environment = new HashMap<String, Object>();
-
-    private final List<Object> objects = new ArrayList<Object>();
+    private final AccessControlContext acc = AccessController.getContext();
+    private final Map<String, Class<? extends ElementHandler>> handlers = new HashMap<>();
+    private final Map<String, Object> environment = new HashMap<>();
+    private final List<Object> objects = new ArrayList<>();
 
     private Reference<ClassLoader> loader;
     private ExceptionListener listener;
@@ -351,23 +355,32 @@
      *
      * @param input  the input source to parse
      */
-    public void parse(InputSource input) {
-        try {
-            SAXParserFactory.newInstance().newSAXParser().parse(input, this);
-        }
-        catch (ParserConfigurationException exception) {
-            handleException(exception);
+    public void parse(final InputSource input) {
+        if ((this.acc == null) && (null != System.getSecurityManager())) {
+            throw new SecurityException("AccessControlContext is not set");
         }
-        catch (SAXException wrapper) {
-            Exception exception = wrapper.getException();
-            if (exception == null) {
-                exception = wrapper;
+        AccessControlContext stack = AccessController.getContext();
+        SharedSecrets.getJavaSecurityAccess().doIntersectionPrivilege(new PrivilegedAction<Void>() {
+            public Void run() {
+                try {
+                    SAXParserFactory.newInstance().newSAXParser().parse(input, DocumentHandler.this);
+                }
+                catch (ParserConfigurationException exception) {
+                    handleException(exception);
+                }
+                catch (SAXException wrapper) {
+                    Exception exception = wrapper.getException();
+                    if (exception == null) {
+                        exception = wrapper;
+                    }
+                    handleException(exception);
+                }
+                catch (IOException exception) {
+                    handleException(exception);
+                }
+                return null;
             }
-            handleException(exception);
-        }
-        catch (IOException exception) {
-            handleException(exception);
-        }
+        }, stack, this.acc);
     }
 
     /**
--- a/src/share/classes/com/sun/beans/decoder/PropertyElementHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/beans/decoder/PropertyElementHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2012, 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
@@ -35,6 +35,8 @@
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
 
+import sun.reflect.misc.MethodUtil;
+
 /**
  * This class is intended to handle &lt;property&gt; element.
  * This element simplifies access to the properties.
@@ -168,11 +170,11 @@
     private static Object getPropertyValue(Object bean, String name, Integer index) throws IllegalAccessException, IntrospectionException, InvocationTargetException, NoSuchMethodException {
         Class<?> type = bean.getClass();
         if (index == null) {
-            return findGetter(type, name).invoke(bean);
+            return MethodUtil.invoke(findGetter(type, name), bean, new Object[] {});
         } else if (type.isArray() && (name == null)) {
             return Array.get(bean, index);
         } else {
-            return findGetter(type, name, int.class).invoke(bean, index);
+            return MethodUtil.invoke(findGetter(type, name, int.class), bean, new Object[] {index});
         }
     }
 
@@ -197,11 +199,11 @@
                 : null;
 
         if (index == null) {
-            findSetter(type, name, param).invoke(bean, value);
+            MethodUtil.invoke(findSetter(type, name, param), bean, new Object[] {value});
         } else if (type.isArray() && (name == null)) {
             Array.set(bean, index, value);
         } else {
-            findSetter(type, name, int.class, param).invoke(bean, index, value);
+            MethodUtil.invoke(findSetter(type, name, int.class, param), bean, new Object[] {index, value});
         }
     }
 
--- a/src/share/classes/com/sun/crypto/provider/KeyProtector.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/crypto/provider/KeyProtector.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 2012, 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
@@ -363,34 +363,3 @@
         super(cipherSpi, provider, transformation);
     }
 }
-
-final class SealedObjectForKeyProtector extends javax.crypto.SealedObject {
-
-    static final long serialVersionUID = -3650226485480866989L;
-
-    SealedObjectForKeyProtector(Serializable object, Cipher c)
-        throws IOException, IllegalBlockSizeException {
-        super(object, c);
-    }
-
-    SealedObjectForKeyProtector(SealedObject so) {
-        super(so);
-    }
-
-    AlgorithmParameters getParameters() {
-        AlgorithmParameters params = null;
-        if (super.encodedParams != null) {
-            try {
-                params = AlgorithmParameters.getInstance("PBE", "SunJCE");
-                params.init(super.encodedParams);
-            } catch (NoSuchProviderException nspe) {
-                // eat.
-            } catch (NoSuchAlgorithmException nsae) {
-                //eat.
-            } catch (IOException ioe) {
-                //eat.
-            }
-        }
-        return params;
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/com/sun/crypto/provider/SealedObjectForKeyProtector.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 1998, 2012, 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 com.sun.crypto.provider;
+
+import java.io.*;
+import java.security.*;
+import javax.crypto.*;
+
+final class SealedObjectForKeyProtector extends SealedObject {
+
+    static final long serialVersionUID = -3650226485480866989L;
+
+    SealedObjectForKeyProtector(Serializable object, Cipher c)
+            throws IOException, IllegalBlockSizeException {
+        super(object, c);
+    }
+
+    SealedObjectForKeyProtector(SealedObject so) {
+        super(so);
+    }
+
+    AlgorithmParameters getParameters() {
+        AlgorithmParameters params = null;
+        if (super.encodedParams != null) {
+            try {
+                params = AlgorithmParameters.getInstance("PBE", "SunJCE");
+                params.init(super.encodedParams);
+            } catch (NoSuchProviderException nspe) {
+                // eat.
+            } catch (NoSuchAlgorithmException nsae) {
+                //eat.
+            } catch (IOException ioe) {
+                //eat.
+            }
+        }
+        return params;
+    }
+}
--- a/src/share/classes/com/sun/jmx/remote/internal/ServerNotifForwarder.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/jmx/remote/internal/ServerNotifForwarder.java	Mon Nov 05 10:33:18 2012 -0500
@@ -68,9 +68,9 @@
         this.notifBuffer = notifBuffer;
         this.connectionId = connectionId;
         connectionTimeout = EnvHelp.getServerConnectionTimeout(env);
-        checkNotificationEmission = EnvHelp.computeBooleanFromString(
-            env,
-            "jmx.remote.x.check.notification.emission",false);
+
+        String stringBoolean = (String) env.get("jmx.remote.x.check.notification.emission");
+        checkNotificationEmission = EnvHelp.computeBooleanFromString( stringBoolean );
         notificationAccessController =
                 EnvHelp.getNotificationAccessController(env);
     }
--- a/src/share/classes/com/sun/jmx/remote/util/EnvHelp.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/jmx/remote/util/EnvHelp.java	Mon Nov 05 10:33:18 2012 -0500
@@ -665,97 +665,57 @@
      * Computes a boolean value from a string value retrieved from a
      * property in the given map.
      *
-     * @param env the environment map.
-     * @param prop the name of the property in the environment map whose
-     * returned string value must be converted into a boolean value.
-     * @param systemProperty if true, consult a system property of the
-     * same name if there is no entry in the environment map.
+     * @param stringBoolean the string value that must be converted
+     * into a boolean value.
      *
      * @return
      *   <ul>
-     *   <li>{@code false} if {@code env.get(prop)} is {@code null}</li>
+     *   <li>{@code false} if {@code stringBoolean} is {@code null}</li>
      *   <li>{@code false} if
-     *       {@code ((String)env.get(prop)).equalsIgnoreCase("false")}
+     *       {@code stringBoolean.equalsIgnoreCase("false")}
      *       is {@code true}</li>
      *   <li>{@code true} if
-     *       {@code ((String)env.get(prop)).equalsIgnoreCase("true")}
+     *       {@code stringBoolean.equalsIgnoreCase("true")}
      *       is {@code true}</li>
      *   </ul>
      *
-     * @throws IllegalArgumentException if {@code env} is {@code null} or
-     * {@code env.get(prop)} is not {@code null} and
+     * @throws IllegalArgumentException if
      * {@code ((String)env.get(prop)).equalsIgnoreCase("false")} and
      * {@code ((String)env.get(prop)).equalsIgnoreCase("true")} are
      * {@code false}.
-     * @throws ClassCastException if {@code env.get(prop)} cannot be cast
-     * to {@code String}.
      */
-    public static boolean computeBooleanFromString(
-            Map<String, ?> env, String prop, boolean systemProperty) {
-
-        if (env == null)
-            throw new IllegalArgumentException("env map cannot be null");
-
+    public static boolean computeBooleanFromString(String stringBoolean) {
         // returns a default value of 'false' if no property is found...
-        return computeBooleanFromString(env,prop,systemProperty,false);
+        return computeBooleanFromString(stringBoolean,false);
     }
 
     /**
      * Computes a boolean value from a string value retrieved from a
      * property in the given map.
      *
-     * @param env the environment map.
-     * @param prop the name of the property in the environment map whose
-     * returned string value must be converted into a boolean value.
-     * @param systemProperty if true, consult a system property of the
-     * same name if there is no entry in the environment map.
+     * @param stringBoolean the string value that must be converted
+     * into a boolean value.
      * @param defaultValue a default value to return in case no property
      *        was defined.
      *
      * @return
      *   <ul>
-     *   <li>{@code defaultValue} if {@code env.get(prop)} is {@code null}
-     *       and {@code systemProperty} is {@code false}</li>
-     *   <li>{@code defaultValue} if {@code env.get(prop)} is {@code null}
-     *       and {@code systemProperty} is {@code true} and
-     *       {@code System.getProperty(prop)} is {@code null}</li>
-     *   <li>{@code false} if {@code env.get(prop)} is {@code null}
-     *       and {@code systemProperty} is {@code true} and
-     *       {@code System.getProperty(prop).equalsIgnoreCase("false")}
-     *       is {@code true}</li>
-     *   <li>{@code true} if {@code env.get(prop)} is {@code null}
-     *       and {@code systemProperty} is {@code true} and
-     *       {@code System.getProperty(prop).equalsIgnoreCase("true")}
-     *       is {@code true}</li>
+     *   <li>{@code defaultValue} if {@code stringBoolean}
+     *   is {@code null}</li>
      *   <li>{@code false} if
-     *       {@code ((String)env.get(prop)).equalsIgnoreCase("false")}
+     *       {@code stringBoolean.equalsIgnoreCase("false")}
      *       is {@code true}</li>
      *   <li>{@code true} if
-     *       {@code ((String)env.get(prop)).equalsIgnoreCase("true")}
+     *       {@code stringBoolean.equalsIgnoreCase("true")}
      *       is {@code true}</li>
      *   </ul>
      *
-     * @throws IllegalArgumentException if {@code env} is {@code null} or
-     * {@code env.get(prop)} is not {@code null} and
+     * @throws IllegalArgumentException if
      * {@code ((String)env.get(prop)).equalsIgnoreCase("false")} and
      * {@code ((String)env.get(prop)).equalsIgnoreCase("true")} are
      * {@code false}.
-     * @throws ClassCastException if {@code env.get(prop)} cannot be cast
-     * to {@code String}.
      */
-    public static boolean computeBooleanFromString(
-            Map<String, ?> env, String prop,
-            boolean systemProperty, boolean defaultValue) {
-
-        if (env == null)
-            throw new IllegalArgumentException("env map cannot be null");
-
-        String stringBoolean = (String) env.get(prop);
-        if (stringBoolean == null && systemProperty) {
-            stringBoolean =
-                    AccessController.doPrivileged(new GetPropertyAction(prop));
-        }
-
+    public static boolean computeBooleanFromString( String stringBoolean, boolean defaultValue) {
         if (stringBoolean == null)
             return defaultValue;
         else if (stringBoolean.equalsIgnoreCase("true"))
@@ -763,8 +723,8 @@
         else if (stringBoolean.equalsIgnoreCase("false"))
             return false;
         else
-            throw new IllegalArgumentException(prop +
-                " must be \"true\" or \"false\" instead of \"" +
+            throw new IllegalArgumentException(
+                "Property value must be \"true\" or \"false\" instead of \"" +
                 stringBoolean + "\"");
     }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/com/sun/jmx/snmp/agent/AcmChecker.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,151 @@
+/*
+ * Copyright (c) 1997, 2007, 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 com.sun.jmx.snmp.agent;
+
+import java.io.Serializable;
+import java.util.Enumeration;
+import java.util.logging.Level;
+import java.util.Vector;
+
+import javax.management.ObjectName;
+import javax.management.MBeanServer;
+import javax.management.MalformedObjectNameException;
+import javax.management.InstanceAlreadyExistsException;
+import javax.management.MBeanRegistrationException;
+import javax.management.NotCompliantMBeanException;
+
+import static com.sun.jmx.defaults.JmxProperties.SNMP_ADAPTOR_LOGGER;
+import com.sun.jmx.snmp.SnmpOid;
+import com.sun.jmx.snmp.SnmpVarBind;
+import com.sun.jmx.snmp.SnmpDefinitions;
+import com.sun.jmx.snmp.SnmpStatusException;
+import com.sun.jmx.snmp.SnmpEngine;
+import com.sun.jmx.snmp.SnmpUnknownModelException;
+import com.sun.jmx.snmp.internal.SnmpAccessControlModel;
+import com.sun.jmx.snmp.internal.SnmpEngineImpl;
+
+/**
+ * Oid Checker makes use of ACM to check each OID during the getnext process.
+ */
+class AcmChecker {
+
+
+    SnmpAccessControlModel model = null;
+    String principal = null;
+    int securityLevel = -1;
+    int version = -1;
+    int pduType = -1;
+    int securityModel = -1;
+    byte[] contextName = null;
+    SnmpEngineImpl engine = null;
+    LongList l = null;
+    AcmChecker(SnmpMibRequest req) {
+        engine = (SnmpEngineImpl) req.getEngine();
+        //We are in V3 architecture, ACM is in the picture.
+        if(engine != null) {
+            if(engine.isCheckOidActivated()) {
+                try {
+                    if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
+                        SNMP_ADAPTOR_LOGGER.logp(Level.FINEST,
+                                SnmpMib.class.getName(),
+                                "AcmChecker(SnmpMibRequest)",
+                                "SNMP V3 Access Control to be done");
+                    }
+                    model = (SnmpAccessControlModel)
+                        engine.getAccessControlSubSystem().
+                        getModel(SnmpDefinitions.snmpVersionThree);
+                    principal = req.getPrincipal();
+                    securityLevel = req.getSecurityLevel();
+                    pduType = req.getPdu().type;
+                    version = req.getRequestPduVersion();
+                    securityModel = req.getSecurityModel();
+                    contextName = req.getAccessContextName();
+                    l = new LongList();
+                    if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
+                        final StringBuilder strb = new StringBuilder()
+                        .append("Will check oid for : principal : ")
+                        .append(principal)
+                        .append("; securityLevel : ").append(securityLevel)
+                        .append("; pduType : ").append(pduType)
+                        .append("; version : ").append(version)
+                        .append("; securityModel : ").append(securityModel)
+                        .append("; contextName : ").append(contextName);
+                        SNMP_ADAPTOR_LOGGER.logp(Level.FINEST,
+                                SnmpMib.class.getName(),
+                                "AcmChecker(SnmpMibRequest)", strb.toString());
+                    }
+
+                }catch(SnmpUnknownModelException e) {
+                    if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
+                        SNMP_ADAPTOR_LOGGER.logp(Level.FINEST,
+                                SnmpMib.class.getName(),
+                                "AcmChecker(SnmpMibRequest)",
+                                "Unknown Model, no ACM check.");
+                    }
+                }
+            }
+        }
+    }
+
+    void add(int index, long arc) {
+        if(model != null)
+            l.add(index, arc);
+    }
+
+    void remove(int index) {
+        if(model != null)
+            l.remove(index);
+    }
+
+    void add(final int at,final long[] src, final int from,
+             final int count) {
+        if(model != null)
+            l.add(at,src,from,count);
+    }
+
+    void remove(final int from, final int count) {
+        if(model != null)
+            l.remove(from,count);
+    }
+
+    void checkCurrentOid() throws SnmpStatusException {
+        if(model != null) {
+            SnmpOid oid = new SnmpOid(l.toArray());
+            if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
+                SNMP_ADAPTOR_LOGGER.logp(Level.FINEST, SnmpMib.class.getName(),
+                        "checkCurrentOid", "Checking access for : " + oid);
+            }
+            model.checkAccess(version,
+                              principal,
+                              securityLevel,
+                              pduType,
+                              securityModel,
+                              contextName,
+                              oid);
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/com/sun/jmx/snmp/agent/LongList.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,235 @@
+/*
+ * Copyright (c) 1997, 2007, 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 com.sun.jmx.snmp.agent;
+
+import java.io.Serializable;
+import java.util.Enumeration;
+import java.util.logging.Level;
+import java.util.Vector;
+
+import javax.management.ObjectName;
+import javax.management.MBeanServer;
+import javax.management.MalformedObjectNameException;
+import javax.management.InstanceAlreadyExistsException;
+import javax.management.MBeanRegistrationException;
+import javax.management.NotCompliantMBeanException;
+
+import static com.sun.jmx.defaults.JmxProperties.SNMP_ADAPTOR_LOGGER;
+import com.sun.jmx.snmp.SnmpOid;
+import com.sun.jmx.snmp.SnmpVarBind;
+import com.sun.jmx.snmp.SnmpDefinitions;
+import com.sun.jmx.snmp.SnmpStatusException;
+import com.sun.jmx.snmp.SnmpEngine;
+import com.sun.jmx.snmp.SnmpUnknownModelException;
+import com.sun.jmx.snmp.internal.SnmpAccessControlModel;
+import com.sun.jmx.snmp.internal.SnmpEngineImpl;
+
+/**
+ * This list is used in order to construct the OID during the getnext.
+ * The constructed oid is checked by the checker AcmChecker.
+ */
+final class LongList {
+
+    public static int DEFAULT_CAPACITY = 10;
+
+    public static int DEFAULT_INCREMENT = 10;
+
+
+    private final int DELTA;
+    private int size;
+
+    /**
+     * The list content. Any access to this variable must be protected
+     * by a synchronized block on the LongList object.
+     * Only read-only action should be performed on this object.
+     **/
+    public  long[] list;
+
+    LongList() {
+        this(DEFAULT_CAPACITY,DEFAULT_INCREMENT);
+    }
+
+    LongList(int initialCapacity) {
+        this(initialCapacity,DEFAULT_INCREMENT);
+    }
+
+    LongList(int initialCapacity, int delta) {
+        size = 0;
+        DELTA = delta;
+        list = allocate(initialCapacity);
+    }
+
+    /**
+     * Same behaviour than size() in {@link java.util.List}.
+     **/
+    public final int size() { return size;}
+
+    /**
+     * Same behaviour than add(long o) in {@link java.util.List}.
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final boolean add(final long o) {
+        if (size >= list.length)
+            resize();
+        list[size++]=o;
+        return true;
+    }
+
+    /**
+     * Same behaviour than add(int index, long o) in
+     * {@link java.util.List}.
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final void add(final int index, final long o) {
+        if (index >  size) throw new IndexOutOfBoundsException();
+        if (index >= list.length) resize();
+        if (index == size) {
+            list[size++]=o;
+            return;
+        }
+
+        java.lang.System.arraycopy(list,index,list,index+1,size-index);
+        list[index]=o;
+        size++;
+    }
+
+    /**
+     * Adds <var>count</var> elements to the list.
+     * @param at index at which the elements must be inserted. The
+     *        first element will be inserted at this index.
+     * @param src  An array containing the elements we want to insert.
+     * @param from Index of the first element from <var>src</var> that
+     *        must be inserted.
+     * @param count number of elements to insert.
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final void add(final int at,final long[] src, final int from,
+                          final int count) {
+        if (count <= 0) return;
+        if (at > size) throw new IndexOutOfBoundsException();
+        ensure(size+count);
+        if (at < size) {
+            java.lang.System.arraycopy(list,at,list,at+count,size-at);
+        }
+        java.lang.System.arraycopy(src,from,list,at,count);
+        size+=count;
+    }
+
+    /**
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final long remove(final int from, final int count) {
+        if (count < 1 || from < 0) return -1;
+        if (from+count > size) return -1;
+
+        final long o = list[from];
+        final int oldsize = size;
+        size = size - count;
+
+        if (from == size) return o;
+
+        java.lang.System.arraycopy(list,from+count,list,from,
+                                   size-from);
+        return o;
+    }
+
+    /**
+     * Same behaviour than remove(int index) in {@link java.util.List}.
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final long remove(final int index) {
+        if (index >= size) return -1;
+        final long o = list[index];
+        list[index]=0;
+        if (index == --size) return o;
+
+        java.lang.System.arraycopy(list,index+1,list,index,
+                                   size-index);
+        return o;
+    }
+
+    /**
+     * Same behaviour than the toArray(long[] a) method in
+     * {@link java.util.List}.
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final long[] toArray(long[] a) {
+        java.lang.System.arraycopy(list,0,a,0,size);
+        return a;
+    }
+
+    /**
+     * Same behaviour than the toArray() method in
+     * {@link java.util.List}.
+     * Any access to this method should be protected in a synchronized
+     * block on the LongList object.
+     **/
+    public final long[] toArray() {
+        return toArray(new long[size]);
+    }
+
+    /**
+     * Resize the list. Increase its capacity by DELTA elements.
+     * Any call to this method must be protected by a synchronized
+     * block on this LongList.
+     **/
+    private final void resize() {
+        final long[] newlist = allocate(list.length + DELTA);
+        java.lang.System.arraycopy(list,0,newlist,0,size);
+        list = newlist;
+    }
+
+    /**
+     * Resize the list. Insure that the new length will be at
+     * least equal to <var>length</var>.
+     * @param length new minimal length requested.
+     * Any call to this method must be protected by a synchronized
+     * block on this LongList.
+     **/
+    private final void ensure(int length) {
+        if (list.length < length) {
+            final int min = list.length+DELTA;
+            length=(length<min)?min:length;
+            final long[] newlist = allocate(length);
+            java.lang.System.arraycopy(list,0,newlist,0,size);
+            list = newlist;
+        }
+    }
+
+    /**
+     * Allocate a new array of object of specified length.
+     **/
+    private final long[] allocate(final int length) {
+        return new long[length];
+    }
+
+}
--- a/src/share/classes/com/sun/jmx/snmp/agent/SnmpMib.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/jmx/snmp/agent/SnmpMib.java	Mon Nov 05 10:33:18 2012 -0500
@@ -48,296 +48,6 @@
 import com.sun.jmx.snmp.internal.SnmpEngineImpl;
 
 /**
- * This list is used in order to construct the OID during the getnext.
- * The constructed oid is checked by the checker AcmChecker.
- */
-final class LongList {
-
-    public static int DEFAULT_CAPACITY = 10;
-
-    public static int DEFAULT_INCREMENT = 10;
-
-
-    private final int DELTA;
-    private int size;
-
-    /**
-     * The list content. Any access to this variable must be protected
-     * by a synchronized block on the LongList object.
-     * Only read-only action should be performed on this object.
-     **/
-    public  long[] list;
-
-    LongList() {
-        this(DEFAULT_CAPACITY,DEFAULT_INCREMENT);
-    }
-
-    LongList(int initialCapacity) {
-        this(initialCapacity,DEFAULT_INCREMENT);
-    }
-
-    LongList(int initialCapacity, int delta) {
-        size = 0;
-        DELTA = delta;
-        list = allocate(initialCapacity);
-    }
-
-    /**
-     * Same behaviour than size() in {@link java.util.List}.
-     **/
-    public final int size() { return size;}
-
-    /**
-     * Same behaviour than add(long o) in {@link java.util.List}.
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final boolean add(final long o) {
-        if (size >= list.length)
-            resize();
-        list[size++]=o;
-        return true;
-    }
-
-    /**
-     * Same behaviour than add(int index, long o) in
-     * {@link java.util.List}.
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final void add(final int index, final long o) {
-        if (index >  size) throw new IndexOutOfBoundsException();
-        if (index >= list.length) resize();
-        if (index == size) {
-            list[size++]=o;
-            return;
-        }
-
-        java.lang.System.arraycopy(list,index,list,index+1,size-index);
-        list[index]=o;
-        size++;
-    }
-
-    /**
-     * Adds <var>count</var> elements to the list.
-     * @param at index at which the elements must be inserted. The
-     *        first element will be inserted at this index.
-     * @param src  An array containing the elements we want to insert.
-     * @param from Index of the first element from <var>src</var> that
-     *        must be inserted.
-     * @param count number of elements to insert.
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final void add(final int at,final long[] src, final int from,
-                          final int count) {
-        if (count <= 0) return;
-        if (at > size) throw new IndexOutOfBoundsException();
-        ensure(size+count);
-        if (at < size) {
-            java.lang.System.arraycopy(list,at,list,at+count,size-at);
-        }
-        java.lang.System.arraycopy(src,from,list,at,count);
-        size+=count;
-    }
-
-    /**
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final long remove(final int from, final int count) {
-        if (count < 1 || from < 0) return -1;
-        if (from+count > size) return -1;
-
-        final long o = list[from];
-        final int oldsize = size;
-        size = size - count;
-
-        if (from == size) return o;
-
-        java.lang.System.arraycopy(list,from+count,list,from,
-                                   size-from);
-        return o;
-    }
-
-    /**
-     * Same behaviour than remove(int index) in {@link java.util.List}.
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final long remove(final int index) {
-        if (index >= size) return -1;
-        final long o = list[index];
-        list[index]=0;
-        if (index == --size) return o;
-
-        java.lang.System.arraycopy(list,index+1,list,index,
-                                   size-index);
-        return o;
-    }
-
-    /**
-     * Same behaviour than the toArray(long[] a) method in
-     * {@link java.util.List}.
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final long[] toArray(long[] a) {
-        java.lang.System.arraycopy(list,0,a,0,size);
-        return a;
-    }
-
-    /**
-     * Same behaviour than the toArray() method in
-     * {@link java.util.List}.
-     * Any access to this method should be protected in a synchronized
-     * block on the LongList object.
-     **/
-    public final long[] toArray() {
-        return toArray(new long[size]);
-    }
-
-    /**
-     * Resize the list. Increase its capacity by DELTA elements.
-     * Any call to this method must be protected by a synchronized
-     * block on this LongList.
-     **/
-    private final void resize() {
-        final long[] newlist = allocate(list.length + DELTA);
-        java.lang.System.arraycopy(list,0,newlist,0,size);
-        list = newlist;
-    }
-
-    /**
-     * Resize the list. Insure that the new length will be at
-     * least equal to <var>length</var>.
-     * @param length new minimal length requested.
-     * Any call to this method must be protected by a synchronized
-     * block on this LongList.
-     **/
-    private final void ensure(int length) {
-        if (list.length < length) {
-            final int min = list.length+DELTA;
-            length=(length<min)?min:length;
-            final long[] newlist = allocate(length);
-            java.lang.System.arraycopy(list,0,newlist,0,size);
-            list = newlist;
-        }
-    }
-
-    /**
-     * Allocate a new array of object of specified length.
-     **/
-    private final long[] allocate(final int length) {
-        return new long[length];
-    }
-
-}
-
-/**
- * Oid Checker makes use of ACM to check each OID during the getnext process.
- */
-class AcmChecker {
-
-
-    SnmpAccessControlModel model = null;
-    String principal = null;
-    int securityLevel = -1;
-    int version = -1;
-    int pduType = -1;
-    int securityModel = -1;
-    byte[] contextName = null;
-    SnmpEngineImpl engine = null;
-    LongList l = null;
-    AcmChecker(SnmpMibRequest req) {
-        engine = (SnmpEngineImpl) req.getEngine();
-        //We are in V3 architecture, ACM is in the picture.
-        if(engine != null) {
-            if(engine.isCheckOidActivated()) {
-                try {
-                    if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
-                        SNMP_ADAPTOR_LOGGER.logp(Level.FINEST,
-                                SnmpMib.class.getName(),
-                                "AcmChecker(SnmpMibRequest)",
-                                "SNMP V3 Access Control to be done");
-                    }
-                    model = (SnmpAccessControlModel)
-                        engine.getAccessControlSubSystem().
-                        getModel(SnmpDefinitions.snmpVersionThree);
-                    principal = req.getPrincipal();
-                    securityLevel = req.getSecurityLevel();
-                    pduType = req.getPdu().type;
-                    version = req.getRequestPduVersion();
-                    securityModel = req.getSecurityModel();
-                    contextName = req.getAccessContextName();
-                    l = new LongList();
-                    if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
-                        final StringBuilder strb = new StringBuilder()
-                        .append("Will check oid for : principal : ")
-                        .append(principal)
-                        .append("; securityLevel : ").append(securityLevel)
-                        .append("; pduType : ").append(pduType)
-                        .append("; version : ").append(version)
-                        .append("; securityModel : ").append(securityModel)
-                        .append("; contextName : ").append(contextName);
-                        SNMP_ADAPTOR_LOGGER.logp(Level.FINEST,
-                                SnmpMib.class.getName(),
-                                "AcmChecker(SnmpMibRequest)", strb.toString());
-                    }
-
-                }catch(SnmpUnknownModelException e) {
-                    if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
-                        SNMP_ADAPTOR_LOGGER.logp(Level.FINEST,
-                                SnmpMib.class.getName(),
-                                "AcmChecker(SnmpMibRequest)",
-                                "Unknown Model, no ACM check.");
-                    }
-                }
-            }
-        }
-    }
-
-    void add(int index, long arc) {
-        if(model != null)
-            l.add(index, arc);
-    }
-
-    void remove(int index) {
-        if(model != null)
-            l.remove(index);
-    }
-
-    void add(final int at,final long[] src, final int from,
-             final int count) {
-        if(model != null)
-            l.add(at,src,from,count);
-    }
-
-    void remove(final int from, final int count) {
-        if(model != null)
-            l.remove(from,count);
-    }
-
-    void checkCurrentOid() throws SnmpStatusException {
-        if(model != null) {
-            SnmpOid oid = new SnmpOid(l.toArray());
-            if (SNMP_ADAPTOR_LOGGER.isLoggable(Level.FINEST)) {
-                SNMP_ADAPTOR_LOGGER.logp(Level.FINEST, SnmpMib.class.getName(),
-                        "checkCurrentOid", "Checking access for : " + oid);
-            }
-            model.checkAccess(version,
-                              principal,
-                              securityLevel,
-                              pduType,
-                              securityModel,
-                              contextName,
-                              oid);
-        }
-    }
-
-}
-
-/**
  * Abstract class for representing an SNMP MIB.
  * <P>
  * When compiling a SNMP MIB, among all the classes generated by
--- a/src/share/classes/com/sun/security/auth/module/Krb5LoginModule.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/com/sun/security/auth/module/Krb5LoginModule.java	Mon Nov 05 10:33:18 2012 -0500
@@ -802,7 +802,7 @@
 
         if (doNotPrompt) {
             throw new LoginException
-                ("Unable to obtain Princpal Name for authentication ");
+                ("Unable to obtain Principal Name for authentication ");
         } else {
             if (callbackHandler == null)
                 throw new LoginException("No CallbackHandler "
--- a/src/share/classes/java/beans/XMLDecoder.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/beans/XMLDecoder.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2012, 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
@@ -29,6 +29,9 @@
 import java.io.Closeable;
 import java.io.InputStream;
 import java.io.IOException;
+import java.security.AccessControlContext;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
 
 import org.xml.sax.InputSource;
 import org.xml.sax.helpers.DefaultHandler;
@@ -61,6 +64,7 @@
  * @author Philip Milne
  */
 public class XMLDecoder implements AutoCloseable {
+    private final AccessControlContext acc = AccessController.getContext();
     private final DocumentHandler handler = new DocumentHandler();
     private final InputSource input;
     private Object owner;
@@ -189,7 +193,15 @@
             return false;
         }
         if (this.array == null) {
-            this.handler.parse(this.input);
+            if ((this.acc == null) && (null != System.getSecurityManager())) {
+                throw new SecurityException("AccessControlContext is not set");
+            }
+            AccessController.doPrivileged(new PrivilegedAction<Void>() {
+                public Void run() {
+                    XMLDecoder.this.handler.parse(XMLDecoder.this.input);
+                    return null;
+                }
+            }, this.acc);
             this.array = this.handler.getObjects();
         }
         return true;
--- a/src/share/classes/java/io/File.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/io/File.java	Mon Nov 05 10:33:18 2012 -0500
@@ -153,7 +153,7 @@
     /**
      * The FileSystem object representing the platform's local file system.
      */
-    private static final FileSystem fs = FileSystem.getFileSystem();
+    private static final FileSystem fs = DefaultFileSystem.getFileSystem();
 
     /**
      * This abstract pathname's normalized pathname string.  A normalized
--- a/src/share/classes/java/io/FilePermission.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/io/FilePermission.java	Mon Nov 05 10:33:18 2012 -0500
@@ -407,7 +407,7 @@
      * @return a hash code value for this object.
      */
     public int hashCode() {
-        return this.cpath.hashCode();
+        return 0;
     }
 
     /**
--- a/src/share/classes/java/io/FileSystem.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/io/FileSystem.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1998, 2005, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1998, 2012, 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
@@ -32,13 +32,6 @@
 
 abstract class FileSystem {
 
-    /**
-     * Return the FileSystem object representing this platform's local
-     * filesystem.
-     */
-    public static native FileSystem getFileSystem();
-
-
     /* -- Normalization and construction -- */
 
     /**
--- a/src/share/classes/java/lang/AbstractStringBuilder.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/AbstractStringBuilder.java	Mon Nov 05 10:33:18 2012 -0500
@@ -70,6 +70,7 @@
      * @return  the length of the sequence of characters currently
      *          represented by this object
      */
+    @Override
     public int length() {
         return count;
     }
@@ -200,6 +201,7 @@
      * @throws     IndexOutOfBoundsException  if {@code index} is
      *             negative or greater than or equal to {@code length()}.
      */
+    @Override
     public char charAt(int index) {
         if ((index < 0) || (index >= count))
             throw new StringIndexOutOfBoundsException(index);
@@ -431,14 +433,29 @@
         return this;
     }
 
+    /**
+     * @since 1.8
+     */
+    AbstractStringBuilder append(AbstractStringBuilder asb) {
+        if (asb == null)
+            return append("null");
+        int len = asb.length();
+        ensureCapacityInternal(count + len);
+        asb.getChars(0, len, value, count);
+        count += len;
+        return this;
+    }
+
     // Documentation in subclasses because of synchro difference
+    @Override
     public AbstractStringBuilder append(CharSequence s) {
         if (s == null)
             s = "null";
         if (s instanceof String)
             return this.append((String)s);
-        if (s instanceof StringBuffer)
-            return this.append((StringBuffer)s);
+        if (s instanceof AbstractStringBuilder)
+            return this.append((AbstractStringBuilder)s);
+
         return this.append(s, 0, s.length());
     }
 
@@ -471,6 +488,7 @@
      *             {@code start} is greater than {@code end} or
      *             {@code end} is greater than {@code s.length()}
      */
+    @Override
     public AbstractStringBuilder append(CharSequence s, int start, int end) {
         if (s == null)
             s = "null";
@@ -585,6 +603,7 @@
      * @param   c   a {@code char}.
      * @return  a reference to this object.
      */
+    @Override
     public AbstractStringBuilder append(char c) {
         ensureCapacityInternal(count + 1);
         value[count++] = c;
@@ -847,6 +866,7 @@
      *          or if <tt>start</tt> is greater than <tt>end</tt>
      * @spec JSR-51
      */
+    @Override
     public CharSequence subSequence(int start, int end) {
         return substring(start, end);
     }
@@ -1397,6 +1417,7 @@
      *
      * @return  a string representation of this sequence of characters.
      */
+    @Override
     public abstract String toString();
 
     /**
--- a/src/share/classes/java/lang/StringBuffer.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/StringBuffer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -149,15 +149,18 @@
         append(seq);
     }
 
+    @Override
     public synchronized int length() {
         return count;
     }
 
+    @Override
     public synchronized int capacity() {
         return value.length;
     }
 
 
+    @Override
     public synchronized void ensureCapacity(int minimumCapacity) {
         if (minimumCapacity > value.length) {
             expandCapacity(minimumCapacity);
@@ -167,6 +170,7 @@
     /**
      * @since      1.5
      */
+    @Override
     public synchronized void trimToSize() {
         super.trimToSize();
     }
@@ -175,6 +179,7 @@
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @see        #length()
      */
+    @Override
     public synchronized void setLength(int newLength) {
         super.setLength(newLength);
     }
@@ -183,6 +188,7 @@
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @see        #length()
      */
+    @Override
     public synchronized char charAt(int index) {
         if ((index < 0) || (index >= count))
             throw new StringIndexOutOfBoundsException(index);
@@ -192,6 +198,7 @@
     /**
      * @since      1.5
      */
+    @Override
     public synchronized int codePointAt(int index) {
         return super.codePointAt(index);
     }
@@ -199,6 +206,7 @@
     /**
      * @since     1.5
      */
+    @Override
     public synchronized int codePointBefore(int index) {
         return super.codePointBefore(index);
     }
@@ -206,6 +214,7 @@
     /**
      * @since     1.5
      */
+    @Override
     public synchronized int codePointCount(int beginIndex, int endIndex) {
         return super.codePointCount(beginIndex, endIndex);
     }
@@ -213,6 +222,7 @@
     /**
      * @since     1.5
      */
+    @Override
     public synchronized int offsetByCodePoints(int index, int codePointOffset) {
         return super.offsetByCodePoints(index, codePointOffset);
     }
@@ -221,6 +231,7 @@
      * @throws NullPointerException {@inheritDoc}
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public synchronized void getChars(int srcBegin, int srcEnd, char[] dst,
                                       int dstBegin)
     {
@@ -231,17 +242,20 @@
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @see        #length()
      */
+    @Override
     public synchronized void setCharAt(int index, char ch) {
         if ((index < 0) || (index >= count))
             throw new StringIndexOutOfBoundsException(index);
         value[index] = ch;
     }
 
+    @Override
     public synchronized StringBuffer append(Object obj) {
         super.append(String.valueOf(obj));
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(String str) {
         super.append(str);
         return this;
@@ -276,6 +290,14 @@
         return this;
     }
 
+    /**
+     * @since 1.8
+     */
+    @Override
+    synchronized StringBuffer append(AbstractStringBuilder asb) {
+        super.append(asb);
+        return this;
+    }
 
     /**
      * Appends the specified {@code CharSequence} to this
@@ -298,27 +320,26 @@
      * @return  a reference to this object.
      * @since 1.5
      */
+    @Override
     public StringBuffer append(CharSequence s) {
-        // Note, synchronization achieved via other invocations
-        if (s == null)
-            s = "null";
-        if (s instanceof String)
-            return this.append((String)s);
-        if (s instanceof StringBuffer)
-            return this.append((StringBuffer)s);
-        return this.append(s, 0, s.length());
+        // Note, synchronization achieved via invocations of other StringBuffer methods after
+        // narrowing of s to specific type
+        super.append(s);
+        return this;
     }
 
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @since      1.5
      */
+    @Override
     public synchronized StringBuffer append(CharSequence s, int start, int end)
     {
         super.append(s, start, end);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(char[] str) {
         super.append(str);
         return this;
@@ -327,21 +348,25 @@
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public synchronized StringBuffer append(char[] str, int offset, int len) {
         super.append(str, offset, len);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(boolean b) {
         super.append(b);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(char c) {
         super.append(c);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(int i) {
         super.append(i);
         return this;
@@ -350,21 +375,25 @@
     /**
      * @since 1.5
      */
+    @Override
     public synchronized StringBuffer appendCodePoint(int codePoint) {
         super.appendCodePoint(codePoint);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(long lng) {
         super.append(lng);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(float f) {
         super.append(f);
         return this;
     }
 
+    @Override
     public synchronized StringBuffer append(double d) {
         super.append(d);
         return this;
@@ -374,6 +403,7 @@
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      * @since      1.2
      */
+    @Override
     public synchronized StringBuffer delete(int start, int end) {
         super.delete(start, end);
         return this;
@@ -383,6 +413,7 @@
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      * @since      1.2
      */
+    @Override
     public synchronized StringBuffer deleteCharAt(int index) {
         super.deleteCharAt(index);
         return this;
@@ -392,6 +423,7 @@
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      * @since      1.2
      */
+    @Override
     public synchronized StringBuffer replace(int start, int end, String str) {
         super.replace(start, end, str);
         return this;
@@ -401,6 +433,7 @@
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      * @since      1.2
      */
+    @Override
     public synchronized String substring(int start) {
         return substring(start, count);
     }
@@ -409,6 +442,7 @@
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @since      1.4
      */
+    @Override
     public synchronized CharSequence subSequence(int start, int end) {
         return super.substring(start, end);
     }
@@ -417,6 +451,7 @@
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      * @since      1.2
      */
+    @Override
     public synchronized String substring(int start, int end) {
         return super.substring(start, end);
     }
@@ -425,6 +460,7 @@
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      * @since      1.2
      */
+    @Override
     public synchronized StringBuffer insert(int index, char[] str, int offset,
                                             int len)
     {
@@ -435,6 +471,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public synchronized StringBuffer insert(int offset, Object obj) {
         super.insert(offset, String.valueOf(obj));
         return this;
@@ -443,6 +480,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public synchronized StringBuffer insert(int offset, String str) {
         super.insert(offset, str);
         return this;
@@ -451,6 +489,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public synchronized StringBuffer insert(int offset, char[] str) {
         super.insert(offset, str);
         return this;
@@ -460,21 +499,21 @@
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @since      1.5
      */
+    @Override
     public StringBuffer insert(int dstOffset, CharSequence s) {
-        // Note, synchronization achieved via other invocations
-        if (s == null)
-            s = "null";
-        if (s instanceof String)
-            return this.insert(dstOffset, (String)s);
-        return this.insert(dstOffset, s, 0, s.length());
+        // Note, synchronization achieved via invocations of other StringBuffer methods
+        // after narrowing of s to specific type
+        super.insert(dstOffset, s);
+        return this;
     }
 
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      * @since      1.5
      */
+    @Override
     public synchronized StringBuffer insert(int dstOffset, CharSequence s,
-                                            int start, int end)
+            int start, int end)
     {
         super.insert(dstOffset, s, start, end);
         return this;
@@ -483,13 +522,18 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
-    public StringBuffer insert(int offset, boolean b) {
-        return insert(offset, String.valueOf(b));
+    @Override
+    public  StringBuffer insert(int offset, boolean b) {
+        // Note, synchronization achieved via invocation of StringBuffer insert(int, String)
+        // after conversion of b to String by super class method
+        super.insert(offset, b);
+        return this;
     }
 
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public synchronized StringBuffer insert(int offset, char c) {
         super.insert(offset, c);
         return this;
@@ -498,54 +542,73 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuffer insert(int offset, int i) {
-        return insert(offset, String.valueOf(i));
+        // Note, synchronization achieved via invocation of StringBuffer insert(int, String)
+        // after conversion of i to String by super class method
+        super.insert(offset, i);
+        return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuffer insert(int offset, long l) {
-        return insert(offset, String.valueOf(l));
+        // Note, synchronization achieved via invocation of StringBuffer insert(int, String)
+        // after conversion of l to String by super class method
+        super.insert(offset, l);
+        return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuffer insert(int offset, float f) {
-        return insert(offset, String.valueOf(f));
+        // Note, synchronization achieved via invocation of StringBuffer insert(int, String)
+        // after conversion of f to String by super class method
+        super.insert(offset, f);
+        return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuffer insert(int offset, double d) {
-        return insert(offset, String.valueOf(d));
+        // Note, synchronization achieved via invocation of StringBuffer insert(int, String)
+        // after conversion of d to String by super class method
+        super.insert(offset, d);
+        return this;
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      * @since      1.4
      */
+    @Override
     public int indexOf(String str) {
-        return indexOf(str, 0);
+        // Note, synchronization achieved via invocations of other StringBuffer methods
+        return super.indexOf(str);
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      * @since      1.4
      */
+    @Override
     public synchronized int indexOf(String str, int fromIndex) {
-        return String.indexOf(value, 0, count,
-                              str.toCharArray(), 0, str.length(), fromIndex);
+        return super.indexOf(str, fromIndex);
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      * @since      1.4
      */
+    @Override
     public int lastIndexOf(String str) {
-        // Note, synchronization achieved via other invocations
+        // Note, synchronization achieved via invocations of other StringBuffer methods
         return lastIndexOf(str, count);
     }
 
@@ -553,19 +616,21 @@
      * @throws NullPointerException {@inheritDoc}
      * @since      1.4
      */
+    @Override
     public synchronized int lastIndexOf(String str, int fromIndex) {
-        return String.lastIndexOf(value, 0, count,
-                              str.toCharArray(), 0, str.length(), fromIndex);
+        return super.lastIndexOf(str, fromIndex);
     }
 
     /**
      * @since   JDK1.0.2
      */
+    @Override
     public synchronized StringBuffer reverse() {
         super.reverse();
         return this;
     }
 
+    @Override
     public synchronized String toString() {
         return new String(value, 0, count);
     }
--- a/src/share/classes/java/lang/StringBuilder.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/StringBuilder.java	Mon Nov 05 10:33:18 2012 -0500
@@ -124,28 +124,17 @@
         append(seq);
     }
 
+    @Override
     public StringBuilder append(Object obj) {
         return append(String.valueOf(obj));
     }
 
+    @Override
     public StringBuilder append(String str) {
         super.append(str);
         return this;
     }
 
-    // Appends the specified string builder to this sequence.
-    private StringBuilder append(StringBuilder sb) {
-        if (sb == null)
-            return append("null");
-        int len = sb.length();
-        int newcount = count + len;
-        if (newcount > value.length)
-            expandCapacity(newcount);
-        sb.getChars(0, len, value, count);
-        count = newcount;
-        return this;
-    }
-
     /**
      * Appends the specified <tt>StringBuffer</tt> to this sequence.
      * <p>
@@ -170,28 +159,22 @@
         return this;
     }
 
-    /**
-     */
+    @Override
     public StringBuilder append(CharSequence s) {
-        if (s == null)
-            s = "null";
-        if (s instanceof String)
-            return this.append((String)s);
-        if (s instanceof StringBuffer)
-            return this.append((StringBuffer)s);
-        if (s instanceof StringBuilder)
-            return this.append((StringBuilder)s);
-        return this.append(s, 0, s.length());
+        super.append(s);
+        return this;
     }
 
     /**
      * @throws     IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder append(CharSequence s, int start, int end) {
         super.append(s, start, end);
         return this;
     }
 
+    @Override
     public StringBuilder append(char[] str) {
         super.append(str);
         return this;
@@ -200,36 +183,43 @@
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder append(char[] str, int offset, int len) {
         super.append(str, offset, len);
         return this;
     }
 
+    @Override
     public StringBuilder append(boolean b) {
         super.append(b);
         return this;
     }
 
+    @Override
     public StringBuilder append(char c) {
         super.append(c);
         return this;
     }
 
+    @Override
     public StringBuilder append(int i) {
         super.append(i);
         return this;
     }
 
+    @Override
     public StringBuilder append(long lng) {
         super.append(lng);
         return this;
     }
 
+    @Override
     public StringBuilder append(float f) {
         super.append(f);
         return this;
     }
 
+    @Override
     public StringBuilder append(double d) {
         super.append(d);
         return this;
@@ -238,6 +228,7 @@
     /**
      * @since 1.5
      */
+    @Override
     public StringBuilder appendCodePoint(int codePoint) {
         super.appendCodePoint(codePoint);
         return this;
@@ -246,6 +237,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder delete(int start, int end) {
         super.delete(start, end);
         return this;
@@ -254,6 +246,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder deleteCharAt(int index) {
         super.deleteCharAt(index);
         return this;
@@ -262,6 +255,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder replace(int start, int end, String str) {
         super.replace(start, end, str);
         return this;
@@ -270,6 +264,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int index, char[] str, int offset,
                                 int len)
     {
@@ -280,13 +275,16 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, Object obj) {
-        return insert(offset, String.valueOf(obj));
+            super.insert(offset, obj);
+            return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, String str) {
         super.insert(offset, str);
         return this;
@@ -295,6 +293,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, char[] str) {
         super.insert(offset, str);
         return this;
@@ -303,17 +302,16 @@
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int dstOffset, CharSequence s) {
-        if (s == null)
-            s = "null";
-        if (s instanceof String)
-            return this.insert(dstOffset, (String)s);
-        return this.insert(dstOffset, s, 0, s.length());
+            super.insert(dstOffset, s);
+            return this;
     }
 
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int dstOffset, CharSequence s,
                                 int start, int end)
     {
@@ -324,6 +322,7 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, boolean b) {
         super.insert(offset, b);
         return this;
@@ -332,6 +331,7 @@
     /**
      * @throws IndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, char c) {
         super.insert(offset, c);
         return this;
@@ -340,66 +340,78 @@
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, int i) {
-        return insert(offset, String.valueOf(i));
+        super.insert(offset, i);
+        return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, long l) {
-        return insert(offset, String.valueOf(l));
+        super.insert(offset, l);
+        return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, float f) {
-        return insert(offset, String.valueOf(f));
+        super.insert(offset, f);
+        return this;
     }
 
     /**
      * @throws StringIndexOutOfBoundsException {@inheritDoc}
      */
+    @Override
     public StringBuilder insert(int offset, double d) {
-        return insert(offset, String.valueOf(d));
+        super.insert(offset, d);
+        return this;
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      */
+    @Override
     public int indexOf(String str) {
-        return indexOf(str, 0);
+        return super.indexOf(str);
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      */
+    @Override
     public int indexOf(String str, int fromIndex) {
-        return String.indexOf(value, 0, count,
-                              str.toCharArray(), 0, str.length(), fromIndex);
+        return super.indexOf(str, fromIndex);
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      */
+    @Override
     public int lastIndexOf(String str) {
-        return lastIndexOf(str, count);
+        return super.lastIndexOf(str);
     }
 
     /**
      * @throws NullPointerException {@inheritDoc}
      */
+    @Override
     public int lastIndexOf(String str, int fromIndex) {
-        return String.lastIndexOf(value, 0, count,
-                              str.toCharArray(), 0, str.length(), fromIndex);
+        return super.lastIndexOf(str, fromIndex);
     }
 
+    @Override
     public StringBuilder reverse() {
         super.reverse();
         return this;
     }
 
+    @Override
     public String toString() {
         // Create a copy, don't share the array
         return new String(value, 0, count);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/java/lang/invoke/AbstractValidatingLambdaMetafactory.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,376 @@
+/*
+ * Copyright (c) 2012, 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 java.lang.invoke;
+
+import java.io.Serializable;
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import sun.invoke.util.Wrapper;
+import static sun.invoke.util.Wrapper.*;
+
+/**
+ * Abstract implementation of a meta-factory which provides parameter unrolling and input validation.
+ *
+ * @author Robert Field
+ */
+/*non-public*/ abstract class AbstractValidatingLambdaMetafactory {
+
+    /*
+     * For context, the comments for the following fields are marked in quotes with their values, given this program:
+     * interface II<T> {  Object foo(T x); }
+     * interface JJ<R extends Number> extends II<R> { }
+     * class CC {  String impl(int i) { return "impl:"+i; }}
+     * class X {
+     *     public static void main(String[] args) {
+     *         JJ<Integer> iii = (new CC())::impl;
+     *         System.out.printf(">>> %s\n", iii.foo(44));
+     * }}
+     */
+    final Class<?> targetClass;               // The class calling the meta-factory via invokedynamic "class X"
+    final MethodType invokedType;             // The type of the invoked method "(CC)II"
+    final Class<?> samBase;                   // The type of the returned instance "interface JJ"
+    final boolean isSerializable;             // Should the returned instance be serializable
+    final MethodHandleInfo samInfo;           // Info about the SAM method handle "MethodHandleInfo[9 II.foo(Object)Object]"
+    final Class<?> samClass;                  // Interface containing the SAM method "interface II"
+    final MethodType samMethodType;           // Type of the SAM method "(Object)Object"
+    final MethodHandleInfo implInfo;          // Info about the implementation method handle "MethodHandleInfo[5 CC.impl(int)String]"
+    final int implKind;                       // Invocation kind for implementation "5"=invokevirtual
+    final boolean implIsInstanceMethod;       // Is the implementation an instance method "true"
+    final Class<?> implDefiningClass;         // Type defining the implementation "class CC"
+    final MethodType implMethodType;          // Type of the implementation method "(int)String"
+    final MethodType instantiatedMethodType;  // Instantiated erased functional interface method type "(Integer)Object"
+
+
+    /**
+     * Meta-factory constructor.
+     *
+     * @param caller Stacked automatically by VM; represents a lookup context with the accessibility privileges
+     *               of the caller.
+     * @param invokedType Stacked automatically by VM; the signature of the invoked method, which includes the
+     *                    expected static type of the returned lambda object, and the static types of the captured
+     *                    arguments for the lambda.  In the event that the implementation method is an instance method,
+     *                    the first argument in the invocation signature will correspond to the receiver.
+     * @param samMethod The primary method in the functional interface to which the lambda or method reference is
+     *                  being converted, represented as a method handle.
+     * @param implMethod The implementation method which should be called (with suitable adaptation of argument
+     *                   types, return types, and adjustment for captured arguments) when methods of the resulting
+     *                   functional interface instance are invoked.
+     * @param instantiatedMethodType The signature of the SAM method from the functional interface's perspective
+     * @throws ReflectiveOperationException
+     */
+    AbstractValidatingLambdaMetafactory(MethodHandles.Lookup caller,
+                                       MethodType invokedType,
+                                       MethodHandle samMethod,
+                                       MethodHandle implMethod,
+                                       MethodType instantiatedMethodType)
+            throws ReflectiveOperationException {
+        this.targetClass = caller.lookupClass();
+        this.invokedType = invokedType;
+
+        this.samBase = invokedType.returnType();
+        this.isSerializable = Serializable.class.isAssignableFrom(samBase);
+
+        this.samInfo = new MethodHandleInfo(samMethod);
+        this.samClass = samInfo.getDeclaringClass();
+        this.samMethodType  = samInfo.getMethodType();
+
+        this.implInfo = new MethodHandleInfo(implMethod);
+        this.implKind = implInfo.getReferenceKind() == MethodHandleInfo.REF_invokeSpecial? MethodHandleInfo.REF_invokeVirtual : implInfo.getReferenceKind(); // @@@ Temp work-around to hotspot incorrectly converting to invokespecial
+        this.implIsInstanceMethod =
+                implKind == MethodHandleInfo.REF_invokeVirtual ||
+                implKind == MethodHandleInfo.REF_invokeSpecial ||
+                implKind == MethodHandleInfo.REF_invokeInterface;
+        this.implDefiningClass = implInfo.getDeclaringClass();
+        this.implMethodType = implInfo.getMethodType();
+
+        this.instantiatedMethodType = instantiatedMethodType;
+    }
+
+    /**
+     * Build the CallSite.
+     *
+     * @return a CallSite, which, when invoked, will return an instance of the
+     * functional interface
+     * @throws ReflectiveOperationException
+     */
+    abstract CallSite buildCallSite() throws ReflectiveOperationException, LambdaConversionException;
+
+    /**
+     * Check the meta-factory arguments for errors
+     * @throws LambdaConversionException if there are improper conversions
+     */
+    void validateMetafactoryArgs() throws LambdaConversionException {
+        // Check target type is a subtype of class where SAM method is defined
+        if (!samClass.isAssignableFrom(samBase)) {
+            throw new LambdaConversionException(String.format("Invalid target type %s for lambda conversion; not a subtype of functional interface %s",
+                    samBase.getName(), samClass.getName()));
+        }
+
+        switch (implKind) {
+            case MethodHandleInfo.REF_invokeInterface:
+            case MethodHandleInfo.REF_invokeVirtual:
+            case MethodHandleInfo.REF_invokeStatic:
+            case MethodHandleInfo.REF_newInvokeSpecial:
+            case MethodHandleInfo.REF_invokeSpecial:
+                break;
+            default:
+                throw new LambdaConversionException(String.format("Unsupported MethodHandle kind: %s", implInfo));
+        }
+
+        // Check arity: optional-receiver + captured + SAM == impl
+        final int implArity = implMethodType.parameterCount();
+        final int receiverArity = implIsInstanceMethod ? 1 : 0;
+        final int capturedArity = invokedType.parameterCount();
+        final int samArity = samMethodType.parameterCount();
+        final int instantiatedArity = instantiatedMethodType.parameterCount();
+        if (implArity + receiverArity != capturedArity + samArity) {
+            throw new LambdaConversionException(String.format("Incorrect number of parameters for %s method %s; %d captured parameters, %d functional interface parameters, %d implementation parameters",
+                    implIsInstanceMethod ? "instance" : "static", implInfo,
+                    capturedArity, samArity, implArity));
+        }
+        if (instantiatedArity != samArity) {
+            throw new LambdaConversionException(String.format("Incorrect number of parameters for %s method %s; %d functional interface parameters, %d SAM method parameters",
+                    implIsInstanceMethod ? "instance" : "static", implInfo,
+                    instantiatedArity, samArity));
+        }
+
+        // If instance: first captured arg (receiver) must be subtype of class where impl method is defined
+        final int capturedStart;
+        final int samStart;
+        if (implIsInstanceMethod) {
+            final Class<?> receiverClass;
+
+            // implementation is an instance method, adjust for receiver in captured variables / SAM arguments
+            if (capturedArity == 0) {
+                // receiver is function parameter
+                capturedStart = 0;
+                samStart = 1;
+                receiverClass = instantiatedMethodType.parameterType(0);
+            } else {
+                // receiver is a captured variable
+                capturedStart = 1;
+                samStart = 0;
+                receiverClass = invokedType.parameterType(0);
+            }
+
+            // check receiver type
+            if (!implDefiningClass.isAssignableFrom(receiverClass)) {
+                throw new LambdaConversionException(String.format("Invalid receiver type %s; not a subtype of implementation type %s",
+                                                                  receiverClass, implDefiningClass));
+            }
+        } else {
+            // no receiver
+            capturedStart = 0;
+            samStart = 0;
+        }
+
+        // Check for exact match on non-receiver captured arguments
+        final int implFromCaptured = capturedArity - capturedStart;
+        for (int i=0; i<implFromCaptured; i++) {
+            Class<?> implParamType = implMethodType.parameterType(i);
+            Class<?> capturedParamType = invokedType.parameterType(i + capturedStart);
+            if (!capturedParamType.equals(implParamType)) {
+                throw new LambdaConversionException(
+                        String.format("Type mismatch in captured lambda parameter %d: expecting %s, found %s", i, capturedParamType, implParamType));
+            }
+        }
+        // Check for adaptation match on SAM arguments
+        final int samOffset = samStart - implFromCaptured;
+        for (int i=implFromCaptured; i<implArity; i++) {
+            Class<?> implParamType = implMethodType.parameterType(i);
+            Class<?> instantiatedParamType = instantiatedMethodType.parameterType(i + samOffset);
+            if (!isAdaptableTo(instantiatedParamType, implParamType, true)) {
+                throw new LambdaConversionException(
+                        String.format("Type mismatch for lambda argument %d: %s is not convertible to %s", i, instantiatedParamType, implParamType));
+            }
+        }
+
+        // Adaptation match: return type
+        Class<?> expectedType = instantiatedMethodType.returnType();
+        Class<?> actualReturnType =
+                (implKind == MethodHandleInfo.REF_newInvokeSpecial)
+                  ? implDefiningClass
+                  : implMethodType.returnType();
+        if (!isAdaptableToAsReturn(actualReturnType, expectedType)) {
+            throw new LambdaConversionException(
+                    String.format("Type mismatch for lambda return: %s is not convertible to %s", actualReturnType, expectedType));
+        }
+     }
+
+    /**
+     * Check type adaptability
+     * @param fromType
+     * @param toType
+     * @param strict If true, do strict checks, else allow that fromType may be parameterized
+     * @return True if 'fromType' can be passed to an argument of 'toType'
+     */
+    private boolean isAdaptableTo(Class<?> fromType, Class<?> toType, boolean strict) {
+        if (fromType.equals(toType)) {
+            return true;
+        }
+        if (fromType.isPrimitive()) {
+            Wrapper wfrom = forPrimitiveType(fromType);
+            if (toType.isPrimitive()) {
+                // both are primitive: widening
+                Wrapper wto = forPrimitiveType(toType);
+                return wto.isConvertibleFrom(wfrom);
+            } else {
+                // from primitive to reference: boxing
+                return toType.isAssignableFrom(wfrom.wrapperType());
+            }
+        } else {
+            if (toType.isPrimitive()) {
+                // from reference to primitive: unboxing
+                Wrapper wfrom;
+                if (isWrapperType(fromType) && (wfrom = forWrapperType(fromType)).primitiveType().isPrimitive()) {
+                    // fromType is a primitive wrapper; unbox+widen
+                    Wrapper wto = forPrimitiveType(toType);
+                    return wto.isConvertibleFrom(wfrom);
+                } else {
+                    // must be convertible to primitive
+                    return !strict;
+                }
+            } else {
+                // both are reference types: fromType should be a superclass of toType.
+                return strict? toType.isAssignableFrom(fromType) : true;
+            }
+        }
+    }
+
+    /**
+     * Check type adaptability for return types -- special handling of void type) and parameterized fromType
+     * @param fromType
+     * @param toType
+     * @return True if 'fromType' can be converted to 'toType'
+     */
+    private boolean isAdaptableToAsReturn(Class<?> fromType, Class<?> toType) {
+        return toType.equals(void.class)
+               || !fromType.equals(void.class) && isAdaptableTo(fromType, toType, false);
+    }
+
+
+    /*********** Logging support -- for debugging only
+    static final Executor logPool = Executors.newSingleThreadExecutor(); // @@@ For debugging only
+    protected static void log(final String s) {
+        MethodHandleProxyLambdaMetafactory.logPool.execute(new Runnable() {
+            @Override
+            public void run() {
+                System.out.println(s);
+            }
+        });
+    }
+
+    protected static void log(final String s, final Throwable e) {
+        MethodHandleProxyLambdaMetafactory.logPool.execute(new Runnable() {
+            @Override
+            public void run() {
+                System.out.println(s);
+                e.printStackTrace(System.out);
+            }
+        });
+    }
+    ***********************/
+
+    /**
+     * Find the SAM method and corresponding methods which should be bridged. SAM method and those to be bridged
+     * will have the same name and number of parameters. Check for matching default methods (non-abstract), they
+     * should not be bridged-over and indicate a complex bridging situation.
+     */
+    class MethodAnalyzer {
+        private final Method[] methods = samBase.getMethods();
+        private final List<Method> methodsFound = new ArrayList<>(methods.length);
+
+        private Method samMethod = null;
+        private final List<Method> methodsToBridge = new ArrayList<>(methods.length);
+        private boolean defaultMethodFound = false;
+
+        MethodAnalyzer() {
+            String samMethodName = samInfo.getName();
+            Class<?>[] samParamTypes = samMethodType.parameterArray();
+            int samParamLength = samParamTypes.length;
+            Class<?> samReturnType = samMethodType.returnType();
+            Class<?> objectClass = Object.class;
+
+            for (Method m : methods) {
+                if (m.getName().equals(samMethodName) && m.getDeclaringClass() != objectClass) {
+                    Class<?>[] mParamTypes = m.getParameterTypes();
+                    if (mParamTypes.length == samParamLength) {
+                        if (Modifier.isAbstract(m.getModifiers())) {
+                            // Exclude methods with duplicate signatures
+                            if (methodUnique(m)) {
+                                if (m.getReturnType().equals(samReturnType) && Arrays.equals(mParamTypes, samParamTypes)) {
+                                    // Exact match, this is the SAM method signature
+                                    samMethod = m;
+                                } else {
+                                    methodsToBridge.add(m);
+                                }
+                            }
+                        } else {
+                            // This is a default method, flag for special processing
+                            defaultMethodFound = true;
+                            // Ignore future matching abstracts.
+                            // Note, due to reabstraction, this is really a punt, hence pass-off to VM
+                            methodUnique(m);
+                        }
+                    }
+                }
+            }
+        }
+
+        Method getSamMethod() {
+            return samMethod;
+        }
+
+        List<Method> getMethodsToBridge() {
+            return methodsToBridge;
+        }
+
+        boolean wasDefaultMethodFound() {
+            return defaultMethodFound;
+        }
+
+        /**
+         * Search the list of previously found methods to determine if there is a method with the same signature
+         * (return and parameter types) as the specified method. If it wasn't found before, add to the found list.
+         *
+         * @param m The method to match
+         * @return False if the method was found, True otherwise
+         */
+        private boolean methodUnique(Method m) {
+            Class<?>[] ptypes = m.getParameterTypes();
+            Class<?> rtype = m.getReturnType();
+            for (Method md : methodsFound) {
+                if (md.getReturnType().equals(rtype) && Arrays.equals(ptypes, md.getParameterTypes())) {
+                    return false;
+                }
+            }
+            methodsFound.add(m);
+            return true;
+        }
+    }
+}
--- a/src/share/classes/java/lang/invoke/BoundMethodHandle.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/BoundMethodHandle.java	Mon Nov 05 10:33:18 2012 -0500
@@ -79,7 +79,7 @@
             default : throw new InternalError("unexpected xtype: " + xtype);
             }
         } catch (Throwable t) {
-            throw new InternalError(t);
+            throw newInternalError(t);
         }
     }
 
@@ -97,7 +97,7 @@
             case 'D': return cloneExtendD(type, form, (double) x);
             }
         } catch (Throwable t) {
-            throw new InternalError(t);
+            throw newInternalError(t);
         }
         throw new InternalError("unexpected type: " + xtype);
     }
@@ -115,7 +115,7 @@
         try {
              return clone(srcType, form);
          } catch (Throwable t) {
-             throw new InternalError(t);
+             throw newInternalError(t);
          }
     }
 
@@ -124,7 +124,7 @@
         try {
              return clone(newType, form.permuteArguments(1, reorder, basicTypes(newType.parameterList())));
          } catch (Throwable t) {
-             throw new InternalError(t);
+             throw newInternalError(t);
          }
     }
 
@@ -166,7 +166,7 @@
             case 'J': return argJ(i);
             }
         } catch (Throwable ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
         throw new InternalError("unexpected type: " + speciesData().types+"."+i);
     }
@@ -192,7 +192,7 @@
         try {
             return (MethodHandle) argL(0);
         } catch (Throwable ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
     }
 
@@ -464,7 +464,7 @@
                     }
                 }
             } catch (Throwable e) {
-                throw new InternalError(e);
+                throw newInternalError(e);
             }
 
             for (SpeciesData d : CACHE.values()) {
@@ -748,7 +748,7 @@
             try {
                 return LOOKUP.findGetter(cbmhClass, fieldName, fieldType);
             } catch (NoSuchFieldException | IllegalAccessException e) {
-                throw new InternalError(e);
+                throw newInternalError(e);
             }
         }
 
@@ -776,7 +776,7 @@
                 Field F_SPECIES_DATA = cbmh.getDeclaredField("SPECIES_DATA");
                 return (SpeciesData) F_SPECIES_DATA.get(null);
             } catch (ReflectiveOperationException ex) {
-                throw new InternalError(ex);
+                throw newInternalError(ex);
             }
         }
 
@@ -802,7 +802,7 @@
             try {
                 return linkConstructor(LOOKUP.findConstructor(cbmh, MethodType.fromMethodDescriptorString(makeSignature(types, true), null)));
             } catch (NoSuchMethodException | IllegalAccessException | IllegalArgumentException | TypeNotPresentException e) {
-                throw new InternalError(e);
+                throw newInternalError(e);
             }
         }
 
@@ -833,7 +833,7 @@
                 linkerMN = MemberName.getFactory().resolveOrFail(REF_invokeStatic, linkerMN, null, NoSuchMethodException.class);
                 assert(linkerMN.isStatic());
             } catch (ReflectiveOperationException ex) {
-                throw new InternalError(ex);
+                throw newInternalError(ex);
             }
             // extend arguments array
             Object[] newArgs = Arrays.copyOf(initName.arguments, initName.arguments.length + 1);
--- a/src/share/classes/java/lang/invoke/CallSite.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/CallSite.java	Mon Nov 05 10:33:18 2012 -0500
@@ -222,7 +222,7 @@
             GET_TARGET = IMPL_LOOKUP.
                 findVirtual(CallSite.class, "getTarget", MethodType.methodType(MethodHandle.class));
         } catch (ReflectiveOperationException e) {
-            throw new InternalError(e);
+            throw newInternalError(e);
         }
     }
 
--- a/src/share/classes/java/lang/invoke/DirectMethodHandle.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/DirectMethodHandle.java	Mon Nov 05 10:33:18 2012 -0500
@@ -218,7 +218,7 @@
         try {
             linker = IMPL_NAMES.resolveOrFail(REF_invokeStatic, linker, null, NoSuchMethodException.class);
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
         final int DMH_THIS    = 0;
         final int ARG_BASE    = 1;
@@ -554,7 +554,7 @@
         try {
             linker = IMPL_NAMES.resolveOrFail(REF_invokeVirtual, linker, null, NoSuchMethodException.class);
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
 
         // What is the external type of the lambda form?
@@ -653,7 +653,7 @@
                 nf.resolve();
             }
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
     }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/java/lang/invoke/InnerClassLambdaMetafactory.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,402 @@
+/*
+ * Copyright (c) 2012, 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 java.lang.invoke;
+
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.lang.reflect.Method;
+import java.security.ProtectionDomain;
+import java.util.concurrent.atomic.AtomicInteger;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+import jdk.internal.org.objectweb.asm.*;
+import static jdk.internal.org.objectweb.asm.Opcodes.*;
+import sun.misc.Unsafe;
+
+/**
+ * InnerClassLambdaMetafactory
+ */
+/*non-public*/ final class InnerClassLambdaMetafactory extends AbstractValidatingLambdaMetafactory {
+    private static final int CLASSFILE_VERSION = 51;
+    private static final Type TYPE_VOID = Type.getType(void.class);
+    private static final String METHOD_DESCRIPTOR_VOID = Type.getMethodDescriptor(Type.VOID_TYPE);
+    private static final String NAME_MAGIC_ACCESSOR_IMPL = "java/lang/invoke/MagicLambdaImpl";
+    private static final String NAME_SERIALIZABLE = "java/io/Serializable";
+    private static final String NAME_CTOR = "<init>";
+
+    //Serialization support
+    private static final String NAME_SERIALIZED_LAMBDA = "com/oracle/java/lang/invoke/SerializedLambdaImpl";
+    private static final String DESCR_METHOD_WRITE_REPLACE = "()Ljava/lang/Object;";
+    private static final String NAME_METHOD_WRITE_REPLACE = "writeReplace";
+    private static final String NAME_OBJECT = "java/lang/Object";
+
+    // Used to ensure that each spun class name is unique
+    private static final AtomicInteger counter = new AtomicInteger(0);
+
+    // See context values in AbstractValidatingLambdaMetafactory
+    private final String implMethodClassName;        // Name of type containing implementation "CC"
+    private final String implMethodName;             // Name of implementation method "impl"
+    private final String implMethodDesc;             // Type descriptor for implementation methods "(I)Ljava/lang/String;"
+    private final Type[] implMethodArgumentTypes;    // ASM types for implementaion method parameters
+    private final Type implMethodReturnType;         // ASM type for implementaion method return type "Ljava/lang/String;"
+    private final MethodType constructorType;        // Generated class constructor type "(CC)void"
+    private final String constructorDesc;            // Type descriptor for constructor "(LCC;)V"
+    private final ClassWriter cw;                    // ASM class writer
+    private final Type[] argTypes;                   // ASM types for the constructor arguments
+    private final String[] argNames;                 // Generated names for the constructor arguments
+    private final String lambdaClassName;            // Generated name for the generated class "X$$Lambda$1"
+    private final Type[] instantiatedArgumentTypes;  // ASM types for the functional interface arguments
+
+    /**
+     * Meta-factory constructor.
+     *
+     * @param caller Stacked automatically by VM; represents a lookup context with the accessibility privileges
+     *               of the caller.
+     * @param invokedType Stacked automatically by VM; the signature of the invoked method, which includes the
+     *                    expected static type of the returned lambda object, and the static types of the captured
+     *                    arguments for the lambda.  In the event that the implementation method is an instance method,
+     *                    the first argument in the invocation signature will correspond to the receiver.
+     * @param samMethod The primary method in the functional interface to which the lambda or method reference is
+     *                  being converted, represented as a method handle.
+     * @param implMethod The implementation method which should be called (with suitable adaptation of argument
+     *                   types, return types, and adjustment for captured arguments) when methods of the resulting
+     *                   functional interface instance are invoked.
+     * @param instantiatedMethodType The signature of the SAM method from the functional interface's perspective
+     * @throws ReflectiveOperationException
+     */
+    public InnerClassLambdaMetafactory(MethodHandles.Lookup caller,
+                                       MethodType invokedType,
+                                       MethodHandle samMethod,
+                                       MethodHandle implMethod,
+                                       MethodType instantiatedMethodType)
+            throws ReflectiveOperationException {
+        super(caller, invokedType, samMethod, implMethod, instantiatedMethodType);
+        implMethodClassName = implDefiningClass.getName().replace('.', '/');
+        implMethodName = implInfo.getName();
+        implMethodDesc = implMethodType.toMethodDescriptorString();
+        Type implMethodAsmType = Type.getMethodType(implMethodDesc);
+        implMethodArgumentTypes = implMethodAsmType.getArgumentTypes();
+        implMethodReturnType = implMethodAsmType.getReturnType();
+        constructorType = invokedType.changeReturnType(Void.TYPE);
+        constructorDesc = constructorType.toMethodDescriptorString();
+        lambdaClassName = targetClass.getName().replace('.', '/') + "$$Lambda$" + counter.incrementAndGet();
+        cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
+        argTypes = Type.getArgumentTypes(constructorDesc);
+        argNames = new String[argTypes.length];
+        for (int i = 0; i < argTypes.length; i++) {
+            argNames[i] = "arg$" + (i + 1);
+        }
+        instantiatedArgumentTypes = Type.getArgumentTypes(instantiatedMethodType.toMethodDescriptorString());
+
+    }
+
+    /**
+     * Build the CallSite. Generate a class file which implements the functional
+     * interface, define the class, if there are no parameters create an instance
+     * of the class which the CallSite will return, otherwise, generate handles
+     * which will call the class' constructor.
+     *
+     * @return a CallSite, which, when invoked, will return an instance of the
+     * functional interface
+     * @throws ReflectiveOperationException
+     */
+    @Override
+    CallSite buildCallSite() throws ReflectiveOperationException, LambdaConversionException {
+        final Class<?> innerClass = spinInnerClass();
+        if (invokedType.parameterCount() == 0) {
+            return new ConstantCallSite(MethodHandles.constant(samBase, innerClass.newInstance()));
+        } else {
+            return new ConstantCallSite(
+                    MethodHandles.Lookup.IMPL_LOOKUP
+                    .findConstructor(innerClass, constructorType)
+                    .asType(constructorType.changeReturnType(samBase)));
+        }
+    }
+
+    /**
+     * Generate a class file which implements the functional
+     * interface, define and return the class.
+     *
+     * @return a Class which implements the functional interface
+     */
+    private <T> Class<? extends T> spinInnerClass() throws LambdaConversionException {
+        String samName = samBase.getName().replace('.', '/');
+
+        cw.visit(CLASSFILE_VERSION, ACC_PUBLIC + ACC_SUPER, lambdaClassName, null, NAME_MAGIC_ACCESSOR_IMPL,
+                 isSerializable ? new String[]{samName, NAME_SERIALIZABLE} : new String[]{samName});
+
+        // Generate final fields to be filled in by constructor
+        for (int i = 0; i < argTypes.length; i++) {
+            FieldVisitor fv = cw.visitField(ACC_PRIVATE + ACC_FINAL, argNames[i], argTypes[i].getDescriptor(), null, null);
+            fv.visitEnd();
+        }
+
+        generateConstructor();
+
+        MethodAnalyzer ma = new MethodAnalyzer();
+
+        // Forward the SAM method
+        if (ma.getSamMethod() == null) {
+            throw new LambdaConversionException(String.format("SAM method not found: %s", samMethodType));
+        } else {
+            generateForwardingMethod(ma.getSamMethod(), false);
+        }
+
+        // Forward the bridges
+        // @@@ Once the VM can do fail-over, uncomment the default method test
+        if (!ma.getMethodsToBridge().isEmpty() /* && !ma.wasDefaultMethodFound() */) {
+            for (Method m : ma.getMethodsToBridge()) {
+                generateForwardingMethod(m, true);
+            }
+        }
+
+        /***** Serialization not yet supported
+        if (isSerializable) {
+            String samMethodName = samInfo.getName();
+            Type samType = Type.getType(samBase);
+            generateSerializationMethod(samType, samMethodName);
+        }
+        ******/
+
+        cw.visitEnd();
+
+        // Define the generated class in this VM.
+
+        final byte[] classBytes = cw.toByteArray();
+
+        if (System.getProperty("debug.dump.generated") != null) {
+            System.out.printf("Loaded: %s (%d bytes) %n", lambdaClassName, classBytes.length);
+            try (FileOutputStream fos = new FileOutputStream(lambdaClassName.replace('/', '.') + ".class")) {
+                fos.write(classBytes);
+            } catch (IOException ex) {
+                Logger.getLogger(InnerClassLambdaMetafactory.class.getName()).log(Level.SEVERE, null, ex);
+            }
+        }
+
+        ClassLoader loader = targetClass.getClassLoader();
+        ProtectionDomain pd = (loader == null) ? null : targetClass.getProtectionDomain();
+        return (Class<? extends T>) Unsafe.getUnsafe().defineClass(lambdaClassName, classBytes, 0, classBytes.length, loader, pd);
+    }
+
+    /**
+     * Generate the constructor for the class
+     */
+    private void generateConstructor() {
+        // Generate constructor
+        MethodVisitor ctor = cw.visitMethod(ACC_PUBLIC, NAME_CTOR, constructorDesc, null, null);
+        ctor.visitCode();
+        ctor.visitVarInsn(ALOAD, 0);
+        ctor.visitMethodInsn(INVOKESPECIAL, NAME_MAGIC_ACCESSOR_IMPL, NAME_CTOR, METHOD_DESCRIPTOR_VOID);
+        int lvIndex = 0;
+        for (int i = 0; i < argTypes.length; i++) {
+            ctor.visitVarInsn(ALOAD, 0);
+            ctor.visitVarInsn(argTypes[i].getOpcode(ILOAD), lvIndex + 1);
+            lvIndex += argTypes[i].getSize();
+            ctor.visitFieldInsn(PUTFIELD, lambdaClassName, argNames[i], argTypes[i].getDescriptor());
+        }
+        ctor.visitInsn(RETURN);
+        ctor.visitMaxs(-1, -1); // Maxs computed by ClassWriter.COMPUTE_MAXS, these arguments ignored
+        ctor.visitEnd();
+    }
+
+    /**
+     * Generate the serialization method (if needed)
+     */
+    /****** This code is out of date -- known to be wrong -- and not currently used ******
+    private void generateSerializationMethod(Type samType, String samMethodName) {
+        String samMethodDesc = samMethodType.toMethodDescriptorString();
+        TypeConvertingMethodAdapter mv = new TypeConvertingMethodAdapter(cw.visitMethod(ACC_PRIVATE + ACC_FINAL, NAME_METHOD_WRITE_REPLACE, DESCR_METHOD_WRITE_REPLACE, null, null));
+
+        mv.visitCode();
+        mv.visitTypeInsn(NEW, NAME_SERIALIZED_LAMBDA);
+        mv.dup();
+        mv.visitLdcInsn(samType);
+        mv.visitLdcInsn(samMethodName);
+        mv.visitLdcInsn(samMethodDesc);
+        mv.visitLdcInsn(Type.getType(implDefiningClass));
+        mv.visitLdcInsn(implMethodName);
+        mv.visitLdcInsn(implMethodDesc);
+
+        mv.iconst(argTypes.length);
+        mv.visitTypeInsn(ANEWARRAY, NAME_OBJECT);
+        for (int i = 0; i < argTypes.length; i++) {
+            mv.dup();
+            mv.iconst(i);
+            mv.visitVarInsn(ALOAD, 0);
+            mv.getfield(lambdaClassName, argNames[i], argTypes[i].getDescriptor());
+            mv.boxIfPrimitive(argTypes[i]);
+            mv.visitInsn(AASTORE);
+        }
+        mv.invokespecial(NAME_SERIALIZED_LAMBDA, NAME_CTOR,
+                           "(Ljava/lang/Class;Ljava/lang/String;Ljava/lang/String;Ljava/lang/Class;Ljava/lang/String;Ljava/lang/String;[Ljava/lang/Object;)V");
+        mv.visitInsn(ARETURN);
+        mv.visitMaxs(-1, -1); // Maxs computed by ClassWriter.COMPUTE_MAXS, these arguments ignored
+        mv.visitEnd();
+    }
+    ********/
+
+    /**
+     * Generate a method which calls the lambda implementation method,
+     * converting arguments, as needed.
+     * @param m The method whose signature should be generated
+     * @param isBridge True if this methods should be flagged as a bridge
+     */
+    private void generateForwardingMethod(Method m, boolean isBridge) {
+        Class<?>[] exceptionTypes = m.getExceptionTypes();
+        String[] exceptionNames = new String[exceptionTypes.length];
+        for (int i = 0; i < exceptionTypes.length; i++) {
+            exceptionNames[i] = exceptionTypes[i].getName().replace('.', '/');
+        }
+        String methodDescriptor = Type.getMethodDescriptor(m);
+        int access = isBridge? ACC_PUBLIC | ACC_BRIDGE : ACC_PUBLIC;
+        MethodVisitor mv = cw.visitMethod(access, m.getName(), methodDescriptor, null, exceptionNames);
+        new ForwardingMethodGenerator(mv).generate(m);
+    }
+
+    /**
+     * This class generates a method body which calls the lambda implementation
+     * method, converting arguments, as needed.
+     */
+    private class ForwardingMethodGenerator extends TypeConvertingMethodAdapter {
+
+        ForwardingMethodGenerator(MethodVisitor mv) {
+            super(mv);
+        }
+
+        void generate(Method m) throws InternalError {
+            visitCode();
+
+            if (implKind == MethodHandleInfo.REF_newInvokeSpecial) {
+                visitTypeInsn(NEW, implMethodClassName);
+                dup();
+            }
+            for (int i = 0; i < argTypes.length; i++) {
+                visitVarInsn(ALOAD, 0);
+                getfield(lambdaClassName, argNames[i], argTypes[i].getDescriptor());
+            }
+
+            convertArgumentTypes(Type.getArgumentTypes(m));
+
+            // Invoke the method we want to forward to
+            visitMethodInsn(invocationOpcode(), implMethodClassName, implMethodName, implMethodDesc);
+
+            // Convert the return value (if any) and return it
+            // Note: if adapting from non-void to void, the 'return' instruction will pop the unneeded result
+            Type samReturnType = Type.getReturnType(m);
+            convertType(implMethodReturnType, samReturnType, samReturnType);
+            areturn(samReturnType);
+
+            visitMaxs(-1, -1); // Maxs computed by ClassWriter.COMPUTE_MAXS, these arguments ignored
+            visitEnd();
+        }
+
+        private void convertArgumentTypes(Type[] samArgumentTypes) {
+            int lvIndex = 0;
+            boolean samIncludesReceiver = implIsInstanceMethod && argTypes.length == 0;
+            int samReceiverLength = samIncludesReceiver ? 1 : 0;
+            if (samIncludesReceiver) {
+                // push receiver
+                Type rcvrType = samArgumentTypes[0];
+                Type instantiatedRcvrType = instantiatedArgumentTypes[0];
+
+                load(lvIndex + 1, rcvrType);
+                lvIndex += rcvrType.getSize();
+                convertType(rcvrType, Type.getType(implDefiningClass), instantiatedRcvrType);
+            }
+            int argOffset = implMethodArgumentTypes.length - samArgumentTypes.length;
+            for (int i = samReceiverLength; i < samArgumentTypes.length; i++) {
+                Type argType = samArgumentTypes[i];
+                Type targetType = implMethodArgumentTypes[argOffset + i];
+                Type instantiatedArgType = instantiatedArgumentTypes[i];
+
+                load(lvIndex + 1, argType);
+                lvIndex += argType.getSize();
+                convertType(argType, targetType, instantiatedArgType);
+            }
+        }
+
+        private void convertType(Type argType, Type targetType, Type functionalType) {
+            convertType(argType.getDescriptor(), targetType.getDescriptor(), functionalType.getDescriptor());
+        }
+
+        private int invocationOpcode() throws InternalError {
+            switch (implKind) {
+                case MethodHandleInfo.REF_invokeStatic:
+                    return INVOKESTATIC;
+                case MethodHandleInfo.REF_newInvokeSpecial:
+                    return INVOKESPECIAL;
+                 case MethodHandleInfo.REF_invokeVirtual:
+                    return INVOKEVIRTUAL;
+                case MethodHandleInfo.REF_invokeInterface:
+                    return INVOKEINTERFACE;
+                case MethodHandleInfo.REF_invokeSpecial:
+                    return INVOKESPECIAL;
+                default:
+                    throw new InternalError("Unexpected invocation kind: " + implKind);
+            }
+        }
+
+        /**
+         * The following methods are copied from
+         * org.objectweb.asm.commons.InstructionAdapter. Part of ASM: a very
+         * small and fast Java bytecode manipulation framework. Copyright (c)
+         * 2000-2005 INRIA, France Telecom All rights reserved.
+         *
+         * Subclass with that (removing these methods) if that package/class is
+         * ever added to the JDK.
+         */
+        private void iconst(final int cst) {
+            if (cst >= -1 && cst <= 5) {
+                mv.visitInsn(Opcodes.ICONST_0 + cst);
+            } else if (cst >= Byte.MIN_VALUE && cst <= Byte.MAX_VALUE) {
+                mv.visitIntInsn(Opcodes.BIPUSH, cst);
+            } else if (cst >= Short.MIN_VALUE && cst <= Short.MAX_VALUE) {
+                mv.visitIntInsn(Opcodes.SIPUSH, cst);
+            } else {
+                mv.visitLdcInsn(cst);
+            }
+        }
+
+        private void load(final int var, final Type type) {
+            mv.visitVarInsn(type.getOpcode(Opcodes.ILOAD), var);
+        }
+
+        private void dup() {
+            mv.visitInsn(Opcodes.DUP);
+        }
+
+        private void areturn(final Type t) {
+            mv.visitInsn(t.getOpcode(Opcodes.IRETURN));
+        }
+
+        private void getfield(
+                final String owner,
+                final String name,
+                final String desc) {
+            mv.visitFieldInsn(Opcodes.GETFIELD, owner, name, desc);
+        }
+    }
+}
--- a/src/share/classes/java/lang/invoke/InvokerBytecodeGenerator.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/InvokerBytecodeGenerator.java	Mon Nov 05 10:33:18 2012 -0500
@@ -138,7 +138,7 @@
                 DUMP_CLASS_FILES_DIR = dumpDir;
                 System.out.println("Dumping class files to "+DUMP_CLASS_FILES_DIR+"/...");
             } catch (Exception e) {
-                throw new InternalError(e);
+                throw newInternalError(e);
             }
         } else {
             DUMP_CLASS_FILES_COUNTERS = null;
@@ -162,7 +162,7 @@
                         file.close();
                         return null;
                     } catch (IOException ex) {
-                        throw new InternalError(ex);
+                        throw newInternalError(ex);
                     }
                 }
             });
@@ -279,7 +279,7 @@
         try {
             member = MEMBERNAME_FACTORY.resolveOrFail(REF_invokeStatic, member, HOST_CLASS, ReflectiveOperationException.class);
         } catch (ReflectiveOperationException e) {
-            throw new InternalError(e);
+            throw newInternalError(e);
         }
         //System.out.println("resolveInvokerMember => "+member);
         return member;
--- a/src/share/classes/java/lang/invoke/Invokers.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/Invokers.java	Mon Nov 05 10:33:18 2012 -0500
@@ -27,6 +27,7 @@
 
 import java.util.Arrays;
 import sun.invoke.empty.Empty;
+import static java.lang.invoke.MethodHandleStatics.*;
 import static java.lang.invoke.MethodHandleNatives.Constants.*;
 import static java.lang.invoke.MethodHandles.Lookup.IMPL_LOOKUP;
 import static java.lang.invoke.LambdaForm.*;
@@ -128,9 +129,8 @@
         try {
             //Lookup.findVirtual(MethodHandle.class, name, type);
             return IMPL_LOOKUP.resolveOrFail(REF_invokeVirtual, MethodHandle.class, name, type);
-
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError("JVM cannot find invoker for "+type, ex);
+            throw newInternalError("JVM cannot find invoker for "+type, ex);
         }
     }
 
@@ -176,7 +176,7 @@
                     .findVirtual(MethodHandle.class, "asSpreader",
                         MethodType.methodType(MethodHandle.class, Class.class, int.class));
             } catch (ReflectiveOperationException ex) {
-                throw new InternalError(ex);
+                throw newInternalError(ex);
             }
             makeSpreader = MethodHandles.insertArguments(makeSpreader, 1, Object[].class, spreadArgCount);
             vaInvoker = MethodHandles.filterArgument(arrayInvoker, 0, makeSpreader);
@@ -215,7 +215,7 @@
                     .findStatic(CallSite.class, "uninitializedCallSite",
                                 MethodType.methodType(Empty.class));
             } catch (ReflectiveOperationException ex) {
-                throw new InternalError(ex);
+                throw newInternalError(ex);
             }
         }
         invoker = MethodHandles.explicitCastArguments(invoker, MethodType.methodType(targetType.returnType()));
@@ -389,7 +389,7 @@
             form.genericInvoker = gamh;
             return gamh;
         } catch (Exception ex) {
-            throw new InternalError("Exception while resolving inexact invoke", ex);
+            throw newInternalError("Exception while resolving inexact invoke", ex);
         }
     }
 
@@ -456,7 +456,7 @@
             NF_getCallSiteTarget.resolve();
             // bound
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
     }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/java/lang/invoke/LambdaConversionException.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2012, 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 java.lang.invoke;
+
+/**
+ * LambdaConversionException
+ */
+public class LambdaConversionException extends Exception {
+    public LambdaConversionException() {
+    }
+
+    public LambdaConversionException(String message) {
+        super(message);
+    }
+
+    public LambdaConversionException(String message, Throwable cause) {
+        super(message, cause);
+    }
+
+    public LambdaConversionException(Throwable cause) {
+        super(cause);
+    }
+
+    public LambdaConversionException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
+        super(message, cause, enableSuppression, writableStackTrace);
+    }
+}
--- a/src/share/classes/java/lang/invoke/LambdaForm.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/LambdaForm.java	Mon Nov 05 10:33:18 2012 -0500
@@ -457,7 +457,7 @@
             isCompiled = true;
             return vmentry;
         } catch (Error | Exception ex) {
-            throw new InternalError(this.toString(), ex);
+            throw newInternalError(this.toString(), ex);
         }
     }
 
@@ -1547,7 +1547,7 @@
             try {
                 zmem = IMPL_NAMES.resolveOrFail(REF_invokeStatic, zmem, null, NoSuchMethodException.class);
             } catch (IllegalAccessException|NoSuchMethodException ex) {
-                throw new InternalError(ex);
+                throw newInternalError(ex);
             }
             NamedFunction zcon = new NamedFunction(zmem);
             Name n = new Name(zcon).newIndex(0);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/java/lang/invoke/LambdaMetafactory.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,178 @@
+/*
+ * Copyright (c) 2012, 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 java.lang.invoke;
+
+/**
+ * <p>Bootstrap methods for converting lambda expressions and method references to functional interface objects.</p>
+ *
+ * <p>For every lambda expressions or method reference in the source code, there is a target type which is a
+ * functional interface. Evaluating a lambda expression produces an object of its target type. The mechanism for
+ * evaluating lambda expressions is to invoke an invokedynamic call site, which takes arguments describing the sole
+ * method of the functional interface and the implementation method, and returns an object (the lambda object) that
+ * implements the target type. Methods of the lambda object invoke the implementation method. For method
+ * references, the implementation method is simply the referenced method; for lambda expressions, the
+ * implementation method is produced by the compiler based on the body of the lambda expression. The methods in
+ * this file are the bootstrap methods for those invokedynamic call sites, called lambda factories, and the
+ * bootstrap methods responsible for linking the lambda factories are called lambda meta-factories.
+ *
+ * <p>The bootstrap methods in this class take the information about the functional interface, the implementation
+ * method, and the static types of the captured lambda arguments, and link a call site which, when invoked,
+ * produces the lambda object.
+ *
+ * <p>Two pieces of information are needed about the functional interface: the SAM method and the type of the SAM
+ * method in the functional interface. The type can be different when parameterized types are used. For example,
+ * consider
+ * <code>interface I&lt;T&gt; { int m(T x); }</code> if this SAM type is used in a lambda
+ * <code>I&lt;Byte&gt; v = ...</code>, we need both the actual SAM method which has the signature
+ * <code>(Object)int</code> and the functional interface type of the method, which has signature
+ * <code>(Byte)int</code>.  The latter is the instantiated erased functional interface method type, or
+ * simply <I>instantiated method type</I>.
+ *
+ * <p>While functional interfaces only have a single abstract method from the language perspective (concrete
+ * methods in Object are and default methods may be present), at the bytecode level they may actually have multiple
+ * methods because of the need for bridge methods. Invoking any of these methods on the lambda object will result
+ * in invoking the implementation method.
+ *
+ * <p>The argument list of the implementation method and the argument list of the functional interface method(s)
+ * may differ in several ways.  The implementation methods may have additional arguments to accommodate arguments
+ * captured by the lambda expression; there may also be differences resulting from permitted adaptations of
+ * arguments, such as casting, boxing, unboxing, and primitive widening. They may also differ because of var-args,
+ * but this is expected to be handled by the compiler.
+ *
+ * <p>Invokedynamic call sites have two argument lists: a static argument list and a dynamic argument list.  The
+ * static argument list lives in the constant pool; the dynamic argument list lives on the operand stack at
+ * invocation time.  The bootstrap method has access to the entire static argument list (which in this case,
+ * contains method handles describing the implementation method and the canonical functional interface method),
+ * as well as a method signature describing the number and static types (but not the values) of the dynamic
+ * arguments, and the static return type of the invokedynamic site.
+ *
+ * <p>The implementation method is described with a method handle. In theory, any method handle could be used.
+ * Currently supported are method handles representing invocation of virtual, interface, constructor and static
+ * methods.
+ *
+ * <p>Assume:
+ * <ul>
+ *      <li>the functional interface method has N arguments, of types (U1, U2, ... Un) and return type Ru</li>
+ *      <li>then the instantiated method type also has N arguments, of types (T1, T2, ... Tn) and return type Rt</li>
+ *      <li>the implementation method has M arguments, of types (A1..Am) and return type Ra,</li>
+ *      <li>the dynamic argument list has K arguments of types (D1..Dk), and the invokedynamic return site has
+ *          type Rd</li>
+ *      <li>the functional interface type is F</li>
+ * </ul>
+ *
+ * <p>The following signature invariants must hold:
+ * <ul>
+ *     <li>Rd is a subtype of F</li>
+ *     <li>For i=1..N, Ti is a subtype of Ui</li>
+ *     <li>Either Rt and Ru are primitive and are the same type, or both are reference types and
+ *         Rt is a subtype of Ru</li>
+ *     <li>If the implementation method is a static method:
+ *     <ul>
+ *         <li>K + N = M</li>
+ *         <li>For i=1..K, Di = Ai</li>
+ *         <li>For i=1..N, Ti is adaptable to Aj, where j=i+k</li>
+ *     </ul></li>
+ *     <li>If the implementation method is an instance method:
+ *     <ul>
+ *         <li>K + N = M + 1</li>
+ *         <li>D1 must be a subtype of the enclosing class for the implementation method</li>
+ *         <li>For i=2..K, Di = Aj, where j=i-1</li>
+ *         <li>For i=1..N, Ti is adaptable to Aj, where j=i+k-1</li>
+ *     </ul></li>
+ *     <li>The return type Rt is void, or the return type Ra is not void and is adaptable to Rt</li>
+ * </ul>
+ *
+ * <p>Note that the potentially parameterized implementation return type provides the value for the SAM. Whereas
+ * the completely known instantiated return type is adapted to the implementation arguments. Because the
+ * instantiated type of the implementation method is not available, the adaptability of return types cannot be
+ * checked as precisely at link-time as the arguments can be checked. Thus a loose version of link-time checking is
+ * done on return type, while a strict version is applied to arguments.
+ *
+ * <p>A type Q is considered adaptable to S as follows:
+ * <table>
+ *     <tr><th>Q</th><th>S</th><th>Link-time checks</th><th>Capture-time checks</th></tr>
+ *     <tr>
+ *         <td>Primitive</td><td>Primitive</td>
+ *         <td>Q can be converted to S via a primitive widening conversion</td>
+ *         <td>None</td>
+ *     </tr>
+ *     <tr>
+ *         <td>Primitive</td><td>Reference</td>
+ *         <td>S is a supertype of the Wrapper(Q)</td>
+ *         <td>Cast from Wrapper(Q) to S</td>
+ *     </tr>
+ *     <tr>
+ *         <td>Reference</td><td>Primitive</td>
+ *         <td>strict: Q is a primitive wrapper and Primitive(Q) can be widened to S
+ *         <br>loose: If Q is a primitive wrapper, check that Primitive(Q) can be widened to S</td>
+ *         <td>If Q is not a primitive wrapper, cast Q to the base Wrapper(S); for example Number for numeric types</td>
+ *     </tr>
+ *     <tr>
+ *         <td>Reference</td><td>Reference</td>
+ *         <td>strict: S is a supertype of Q
+ *         <br>loose: none</td>
+ *         <td>Cast from Q to S</td>
+ *     </tr>
+ * </table>
+ *
+ *
+ */
+public class LambdaMetafactory {
+
+    /**
+     * Standard meta-factory for conversion of lambda expressions or method references to functional interfaces.
+     *
+     * @param caller Stacked automatically by VM; represents a lookup context with the accessibility privileges
+     *               of the caller.
+     * @param invokedName Stacked automatically by VM; the name of the invoked method as it appears at the call site.
+     *                    Currently unused.
+     * @param invokedType Stacked automatically by VM; the signature of the invoked method, which includes the
+     *                    expected static type of the returned lambda object, and the static types of the captured
+     *                    arguments for the lambda.  In the event that the implementation method is an instance method,
+     *                    the first argument in the invocation signature will correspond to the receiver.
+     * @param samMethod The primary method in the functional interface to which the lambda or method reference is
+     *                  being converted, represented as a method handle.
+     * @param implMethod The implementation method which should be called (with suitable adaptation of argument
+     *                   types, return types, and adjustment for captured arguments) when methods of the resulting
+     *                   functional interface instance are invoked.
+     * @param instantiatedMethodType The signature of the SAM method from the functional interface's perspective
+     * @return a CallSite, which, when invoked, will return an instance of the functional interface
+     * @throws ReflectiveOperationException
+     * @throws LambdaConversionException If any of the meta-factory protocol invariants are violated
+     */
+    public static CallSite metaFactory(MethodHandles.Lookup caller,
+                                       String invokedName,
+                                       MethodType invokedType,
+                                       MethodHandle samMethod,
+                                       MethodHandle implMethod,
+                                       MethodType instantiatedMethodType)
+                   throws ReflectiveOperationException, LambdaConversionException {
+        AbstractValidatingLambdaMetafactory mf;
+        mf = new InnerClassLambdaMetafactory(caller, invokedType, samMethod, implMethod, instantiatedMethodType);
+        mf.validateMetafactoryArgs();
+        return mf.buildCallSite();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/java/lang/invoke/MagicLambdaImpl.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,39 @@
+/*
+ * Copyright (c) 2012, 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 java.lang.invoke;
+
+/** <P> MagicLambdaImpl (named for similarity to MagicAccessorImpl and
+ others, not because it actually implements an interface) is a
+ marker class in the hierarchy. All subclasses of this class are
+ "magically" granted access by the VM to otherwise inaccessible
+ fields and methods of other classes. It is distinct from MagicAccessorImpl
+ because, while we want to bypass accessibility checks, we do not want to
+ bypass verification.</P>
+
+ <P> Do not change the name of this class without also changing the
+ VM's code. </P> */
+
+class MagicLambdaImpl {
+}
--- a/src/share/classes/java/lang/invoke/MemberName.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/MemberName.java	Mon Nov 05 10:33:18 2012 -0500
@@ -558,7 +558,7 @@
         try {
             return (MemberName) super.clone();
         } catch (CloneNotSupportedException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
      }
 
--- a/src/share/classes/java/lang/invoke/MethodHandle.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/MethodHandle.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1372,7 +1372,7 @@
             NF_reinvokerTarget = new LambdaForm.NamedFunction(MethodHandle.class
                 .getDeclaredMethod("reinvokerTarget"));
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
     }
 
@@ -1397,7 +1397,7 @@
         try {
             FORM_OFFSET = UNSAFE.objectFieldOffset(MethodHandle.class.getDeclaredField("form"));
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
     }
 }
--- a/src/share/classes/java/lang/invoke/MethodHandleImpl.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/MethodHandleImpl.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2012, 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
@@ -25,13 +25,14 @@
 
 package java.lang.invoke;
 
-import sun.invoke.util.VerifyType;
-
+import java.security.AccessController;
+import java.security.PrivilegedAction;
 import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.HashMap;
 import sun.invoke.empty.Empty;
 import sun.invoke.util.ValueConversions;
+import sun.invoke.util.VerifyType;
 import sun.invoke.util.Wrapper;
 import static java.lang.invoke.LambdaForm.*;
 import static java.lang.invoke.MethodHandleStatics.*;
@@ -478,7 +479,7 @@
                     .getDeclaredMethod("checkSpreadArgument", Object.class, int.class));
             NF_checkSpreadArgument.resolve();
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw newInternalError(ex);
         }
     }
 
@@ -781,4 +782,168 @@
         return mh;
     }
 
+    /**
+     * Create an alias for the method handle which, when called,
+     * appears to be called from the same class loader and protection domain
+     * as hostClass.
+     * This is an expensive no-op unless the method which is called
+     * is sensitive to its caller.  A small number of system methods
+     * are in this category, including Class.forName and Method.invoke.
+     */
+    static
+    MethodHandle bindCaller(MethodHandle mh, Class<?> hostClass) {
+        return BindCaller.bindCaller(mh, hostClass);
+    }
+
+    // Put the whole mess into its own nested class.
+    // That way we can lazily load the code and set up the constants.
+    private static class BindCaller {
+        static
+        MethodHandle bindCaller(MethodHandle mh, Class<?> hostClass) {
+            // Do not use this function to inject calls into system classes.
+            if (hostClass == null) {
+                hostClass = C_Trampoline;
+            } else if (hostClass.isArray() ||
+                       hostClass.isPrimitive() ||
+                       hostClass.getName().startsWith("java.") ||
+                       hostClass.getName().startsWith("sun.")) {
+                throw new InternalError();  // does not happen, and should not anyway
+            }
+            // For simplicity, convert mh to a varargs-like method.
+            MethodHandle vamh = prepareForInvoker(mh);
+            // Cache the result of makeInjectedInvoker once per argument class.
+            MethodHandle bccInvoker = CV_makeInjectedInvoker.get(hostClass);
+            return restoreToType(bccInvoker.bindTo(vamh), mh.type());
+        }
+
+        // This class ("Trampoline") is known to be inside a dead-end class loader.
+        // Inject all doubtful calls into this class.
+        private static Class<?> C_Trampoline;
+        static {
+            Class<?> tramp = null;
+            try {
+                final int FRAME_COUNT_ARG = 1;  // [0] Reflection [1] Trampoline
+                java.lang.reflect.Method gcc = sun.reflect.Reflection.class.getMethod("getCallerClass", int.class);
+                tramp = (Class<?>) sun.reflect.misc.MethodUtil.invoke(gcc, null, new Object[]{ FRAME_COUNT_ARG });
+                if (tramp.getClassLoader() == BindCaller.class.getClassLoader())
+                    throw new RuntimeException(tramp.getName()+" class loader");
+            } catch (Throwable ex) {
+                throw new InternalError(ex);
+            }
+            C_Trampoline = tramp;
+        }
+
+        private static MethodHandle makeInjectedInvoker(Class<?> hostClass) {
+            Class<?> bcc = UNSAFE.defineAnonymousClass(hostClass, T_BYTES, null);
+            if (hostClass.getClassLoader() != bcc.getClassLoader())
+                throw new InternalError(hostClass.getName()+" (CL)");
+            try {
+                if (hostClass.getProtectionDomain() != bcc.getProtectionDomain())
+                    throw new InternalError(hostClass.getName()+" (PD)");
+            } catch (SecurityException ex) {
+                // Self-check was blocked by security manager.  This is OK.
+                // In fact the whole try body could be turned into an assertion.
+            }
+            try {
+                MethodHandle init = IMPL_LOOKUP.findStatic(bcc, "init", MethodType.methodType(void.class));
+                init.invokeExact();  // force initialization of the class
+            } catch (Throwable ex) {
+                throw uncaughtException(ex);
+            }
+            MethodHandle bccInvoker;
+            try {
+                MethodType invokerMT = MethodType.methodType(Object.class, MethodHandle.class, Object[].class);
+                bccInvoker = IMPL_LOOKUP.findStatic(bcc, "invoke_V", invokerMT);
+            } catch (ReflectiveOperationException ex) {
+                throw uncaughtException(ex);
+            }
+            // Test the invoker, to ensure that it really injects into the right place.
+            try {
+                MethodHandle vamh = prepareForInvoker(MH_checkCallerClass);
+                Object ok = bccInvoker.invokeExact(vamh, new Object[]{hostClass, bcc});
+            } catch (Throwable ex) {
+                throw new InternalError(ex);
+            }
+            return bccInvoker;
+        }
+        private static ClassValue<MethodHandle> CV_makeInjectedInvoker = new ClassValue<MethodHandle>() {
+            @Override protected MethodHandle computeValue(Class<?> hostClass) {
+                return makeInjectedInvoker(hostClass);
+            }
+        };
+
+        // Adapt mh so that it can be called directly from an injected invoker:
+        private static MethodHandle prepareForInvoker(MethodHandle mh) {
+            mh = mh.asFixedArity();
+            MethodType mt = mh.type();
+            int arity = mt.parameterCount();
+            MethodHandle vamh = mh.asType(mt.generic());
+            vamh.internalForm().compileToBytecode();  // eliminate LFI stack frames
+            vamh = vamh.asSpreader(Object[].class, arity);
+            vamh.internalForm().compileToBytecode();  // eliminate LFI stack frames
+            return vamh;
+        }
+
+        // Undo the adapter effect of prepareForInvoker:
+        private static MethodHandle restoreToType(MethodHandle vamh, MethodType type) {
+            return vamh.asCollector(Object[].class, type.parameterCount()).asType(type);
+        }
+
+        private static final MethodHandle MH_checkCallerClass;
+        static {
+            final Class<?> THIS_CLASS = BindCaller.class;
+            assert(checkCallerClass(THIS_CLASS, THIS_CLASS));
+            try {
+                MH_checkCallerClass = IMPL_LOOKUP
+                    .findStatic(THIS_CLASS, "checkCallerClass",
+                                MethodType.methodType(boolean.class, Class.class, Class.class));
+                assert((boolean) MH_checkCallerClass.invokeExact(THIS_CLASS, THIS_CLASS));
+            } catch (Throwable ex) {
+                throw new InternalError(ex);
+            }
+        }
+
+        private static boolean checkCallerClass(Class<?> expected, Class<?> expected2) {
+            final int FRAME_COUNT_ARG = 2;  // [0] Reflection [1] BindCaller [2] Expected
+            Class<?> actual = sun.reflect.Reflection.getCallerClass(FRAME_COUNT_ARG);
+            if (actual != expected && actual != expected2)
+                throw new InternalError("found "+actual.getName()+", expected "+expected.getName()
+                                        +(expected == expected2 ? "" : ", or else "+expected2.getName()));
+            return true;
+        }
+
+        private static final byte[] T_BYTES;
+        static {
+            final Object[] values = {null};
+            AccessController.doPrivileged(new PrivilegedAction<Void>() {
+                    public Void run() {
+                        try {
+                            Class<T> tClass = T.class;
+                            String tName = tClass.getName();
+                            String tResource = tName.substring(tName.lastIndexOf('.')+1)+".class";
+                            java.net.URLConnection uconn = tClass.getResource(tResource).openConnection();
+                            int len = uconn.getContentLength();
+                            byte[] bytes = new byte[len];
+                            try (java.io.InputStream str = uconn.getInputStream()) {
+                                int nr = str.read(bytes);
+                                if (nr != len)  throw new java.io.IOException(tResource);
+                            }
+                            values[0] = bytes;
+                        } catch (java.io.IOException ex) {
+                            throw new InternalError(ex);
+                        }
+                        return null;
+                    }
+                });
+            T_BYTES = (byte[]) values[0];
+        }
+
+        // The following class is used as a template for Unsafe.defineAnonymousClass:
+        private static class T {
+            static void init() { }  // side effect: initializes this class
+            static Object invoke_V(MethodHandle vamh, Object[] args) throws Throwable {
+                return vamh.invokeExact(args);
+            }
+        }
+    }
 }
--- a/src/share/classes/java/lang/invoke/MethodHandleNatives.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/MethodHandleNatives.java	Mon Nov 05 10:33:18 2012 -0500
@@ -385,4 +385,101 @@
             throw err;
         }
     }
+
+    /**
+     * Is this method a caller-sensitive method?
+     * I.e., does it call Reflection.getCallerClass or a similer method
+     * to ask about the identity of its caller?
+     */
+    // FIXME: Replace this pattern match by an annotation @sun.reflect.CallerSensitive.
+    static boolean isCallerSensitive(MemberName mem) {
+        assert(mem.isInvocable());
+        Class<?> defc = mem.getDeclaringClass();
+        switch (mem.getName()) {
+        case "doPrivileged":
+            return defc == java.security.AccessController.class;
+        case "getUnsafe":
+            return defc == sun.misc.Unsafe.class;
+        case "lookup":
+            return defc == java.lang.invoke.MethodHandles.class;
+        case "invoke":
+            return defc == java.lang.reflect.Method.class;
+        case "get":
+        case "getBoolean":
+        case "getByte":
+        case "getChar":
+        case "getShort":
+        case "getInt":
+        case "getLong":
+        case "getFloat":
+        case "getDouble":
+        case "set":
+        case "setBoolean":
+        case "setByte":
+        case "setChar":
+        case "setShort":
+        case "setInt":
+        case "setLong":
+        case "setFloat":
+        case "setDouble":
+            return defc == java.lang.reflect.Field.class;
+        case "newInstance":
+            if (defc == java.lang.reflect.Constructor.class)  return true;
+            if (defc == java.lang.Class.class)  return true;
+            break;
+        case "forName":
+        case "getClassLoader":
+        case "getClasses":
+        case "getFields":
+        case "getMethods":
+        case "getConstructors":
+        case "getDeclaredClasses":
+        case "getDeclaredFields":
+        case "getDeclaredMethods":
+        case "getDeclaredConstructors":
+        case "getField":
+        case "getMethod":
+        case "getConstructor":
+        case "getDeclaredField":
+        case "getDeclaredMethod":
+        case "getDeclaredConstructor":
+            return defc == java.lang.Class.class;
+        case "getConnection":
+        case "getDriver":
+        case "getDrivers":
+        case "deregisterDriver":
+            return defc == java.sql.DriverManager.class;
+        case "newUpdater":
+            if (defc == java.util.concurrent.atomic.AtomicIntegerFieldUpdater.class)  return true;
+            if (defc == java.util.concurrent.atomic.AtomicLongFieldUpdater.class)  return true;
+            if (defc == java.util.concurrent.atomic.AtomicReferenceFieldUpdater.class)  return true;
+            break;
+        case "getContextClassLoader":
+            return defc == java.lang.Thread.class;
+        case "getPackage":
+        case "getPackages":
+            return defc == java.lang.Package.class;
+        case "getParent":
+        case "getSystemClassLoader":
+            return defc == java.lang.ClassLoader.class;
+        case "load":
+        case "loadLibrary":
+            if (defc == java.lang.Runtime.class)  return true;
+            if (defc == java.lang.System.class)  return true;
+            break;
+        case "getCallerClass":
+            if (defc == sun.reflect.Reflection.class)  return true;
+            if (defc == java.lang.System.class)  return true;
+            break;
+        case "getCallerClassLoader":
+            return defc == java.lang.ClassLoader.class;
+        case "getProxyClass":
+        case "newProxyInstance":
+            return defc == java.lang.reflect.Proxy.class;
+        case "getBundle":
+        case "clearCache":
+            return defc == java.util.ResourceBundle.class;
+        }
+        return false;
+    }
 }
--- a/src/share/classes/java/lang/invoke/MethodHandleStatics.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/MethodHandleStatics.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 2012, 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
@@ -93,6 +93,12 @@
     }
 
     // handy shared exception makers (they simplify the common case code)
+    /*non-public*/ static InternalError newInternalError(String message, Throwable cause) {
+        return new InternalError(message, cause);
+    }
+    /*non-public*/ static InternalError newInternalError(Throwable cause) {
+        return new InternalError(cause);
+    }
     /*non-public*/ static RuntimeException newIllegalStateException(String message) {
         return new IllegalStateException(message);
     }
@@ -108,8 +114,8 @@
     /*non-public*/ static RuntimeException newIllegalArgumentException(String message, Object obj, Object obj2) {
         return new IllegalArgumentException(message(message, obj, obj2));
     }
-    /*non-public*/ static Error uncaughtException(Exception ex) {
-        throw new InternalError("uncaught exception", ex);
+    /*non-public*/ static Error uncaughtException(Throwable ex) {
+        throw newInternalError("uncaught exception", ex);
     }
     static Error NYI() {
         throw new AssertionError("NYI");
--- a/src/share/classes/java/lang/invoke/MethodHandles.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/lang/invoke/MethodHandles.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2012, 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
@@ -329,6 +329,7 @@
      *     where {@code defcPkg} is the package of {@code defc}.
      * </ul>
      */
+    // FIXME in MR1: clarify that the bytecode behavior of a caller-ID method (like Class.forName) is relative to the lookupClass used to create the method handle, not the dynamic caller of the method handle
     public static final
     class Lookup {
         /** The class on behalf of whom the lookup is being performed. */
@@ -1209,6 +1210,7 @@
             if (method.isMethodHandleInvoke())
                 return fakeMethodHandleInvoke(method);
             MethodHandle mh = DirectMethodHandle.make(refc, method);
+            mh = maybeBindCaller(method, mh);
             mh = mh.setVarargs(method);
             if (doRestrict)
                 mh = restrictReceiver(method, mh, lookupClass());
@@ -1217,6 +1219,16 @@
         private MethodHandle fakeMethodHandleInvoke(MemberName method) {
             return throwException(method.getReturnType(), UnsupportedOperationException.class);
         }
+        private MethodHandle maybeBindCaller(MemberName method, MethodHandle mh) throws IllegalAccessException {
+            if (allowedModes == TRUSTED || !MethodHandleNatives.isCallerSensitive(method))
+                return mh;
+            Class<?> hostClass = lookupClass;
+            if ((allowedModes & PRIVATE) == 0)  // caller must use full-power lookup
+                hostClass = null;
+            MethodHandle cbmh = MethodHandleImpl.bindCaller(mh, hostClass);
+            // Note: caller will apply varargs after this step happens.
+            return cbmh;
+        }
         private MethodHandle getDirectField(byte refKind, Class<?> refc, MemberName field) throws IllegalAccessException {
             checkField(refKind, refc, field);
             MethodHandle mh = DirectMethodHandle.make(refc, field);
@@ -1229,6 +1241,7 @@
         private MethodHandle getDirectConstructor(Class<?> refc, MemberName ctor) throws IllegalAccessException {
             assert(ctor.isConstructor());
             checkAccess(REF_newInvokeSpecial, refc, ctor);
+            assert(!MethodHandleNatives.isCallerSensitive(ctor));  // maybeBindCaller not relevant here
             return DirectMethodHandle.make(ctor).setVarargs(ctor);
         }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/java/lang/invoke/TypeConvertingMethodAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,267 @@
+/*
+ * Copyright (c) 2012, 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 java.lang.invoke;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import sun.invoke.util.Wrapper;
+import static sun.invoke.util.Wrapper.*;
+
+class TypeConvertingMethodAdapter extends MethodVisitor {
+
+    TypeConvertingMethodAdapter(MethodVisitor mv) {
+        super(Opcodes.ASM4, mv);
+    }
+
+    private static final int NUM_WRAPPERS = Wrapper.values().length;
+
+    private static final String NAME_OBJECT = "java/lang/Object";
+    private static final String WRAPPER_PREFIX = "Ljava/lang/";
+
+    // Same for all primitives; name of the boxing method
+    private static final String NAME_BOX_METHOD = "valueOf";
+
+    // Table of opcodes for widening primitive conversions; NOP = no conversion
+    private static final int[][] wideningOpcodes = new int[NUM_WRAPPERS][NUM_WRAPPERS];
+
+    private static final Wrapper[] FROM_WRAPPER_NAME = new Wrapper[16];
+
+    static {
+        for (Wrapper w : Wrapper.values()) {
+            if (w.basicTypeChar() != 'L') {
+                int wi = hashWrapperName(w.wrapperSimpleName());
+                assert (FROM_WRAPPER_NAME[wi] == null);
+                FROM_WRAPPER_NAME[wi] = w;
+            }
+        }
+
+        for (int i = 0; i < NUM_WRAPPERS; i++) {
+            for (int j = 0; j < NUM_WRAPPERS; j++) {
+                wideningOpcodes[i][j] = Opcodes.NOP;
+            }
+        }
+
+        initWidening(LONG,   Opcodes.I2L, BYTE, SHORT, INT, CHAR);
+        initWidening(LONG,   Opcodes.F2L, FLOAT);
+        initWidening(FLOAT,  Opcodes.I2F, BYTE, SHORT, INT, CHAR);
+        initWidening(FLOAT,  Opcodes.L2F, LONG);
+        initWidening(DOUBLE, Opcodes.I2D, BYTE, SHORT, INT, CHAR);
+        initWidening(DOUBLE, Opcodes.F2D, FLOAT);
+        initWidening(DOUBLE, Opcodes.L2D, LONG);
+    }
+
+    private static void initWidening(Wrapper to, int opcode, Wrapper... from) {
+        for (Wrapper f : from) {
+            wideningOpcodes[f.ordinal()][to.ordinal()] = opcode;
+        }
+    }
+
+    /**
+     * Class name to Wrapper hash, derived from Wrapper.hashWrap()
+     * @param xn
+     * @return The hash code 0-15
+     */
+    private static int hashWrapperName(String xn) {
+        if (xn.length() < 3) {
+            return 0;
+        }
+        return (3 * xn.charAt(1) + xn.charAt(2)) % 16;
+    }
+
+    private Wrapper wrapperOrNullFromDescriptor(String desc) {
+        if (!desc.startsWith(WRAPPER_PREFIX)) {
+            // Not a class type (array or method), so not a boxed type
+            // or not in the right package
+            return null;
+        }
+        // Pare it down to the simple class name
+        String cname = desc.substring(WRAPPER_PREFIX.length(), desc.length() - 1);
+        // Hash to a Wrapper
+        Wrapper w = FROM_WRAPPER_NAME[hashWrapperName(cname)];
+        if (w == null || w.wrapperSimpleName().equals(cname)) {
+            return w;
+        } else {
+            return null;
+        }
+    }
+
+    private static String wrapperName(Wrapper w) {
+        return "java/lang/" + w.wrapperSimpleName();
+    }
+
+    private static String unboxMethod(Wrapper w) {
+        return w.primitiveSimpleName() + "Value";
+    }
+
+    private static String boxingDescriptor(Wrapper w) {
+        return String.format("(%s)L%s;", w.basicTypeChar(), wrapperName(w));
+    }
+
+    private static String unboxingDescriptor(Wrapper w) {
+        return "()" + w.basicTypeChar();
+    }
+
+    void boxIfPrimitive(Wrapper w) {
+        if (w.zero() != null) {
+            box(w);
+        }
+    }
+
+    void widen(Wrapper ws, Wrapper wt) {
+        if (ws != wt) {
+            int opcode = wideningOpcodes[ws.ordinal()][wt.ordinal()];
+            if (opcode != Opcodes.NOP) {
+                visitInsn(opcode);
+            }
+        }
+    }
+
+    void box(Wrapper w) {
+        visitMethodInsn(Opcodes.INVOKESTATIC,
+                wrapperName(w),
+                NAME_BOX_METHOD,
+                boxingDescriptor(w));
+    }
+
+    /**
+     * Convert types by unboxing. The source type is known to be a primitive wrapper.
+     * @param ws A primitive wrapper corresponding to wrapped reference source type
+     * @param wt A primitive wrapper being converted to
+     */
+    void unbox(String sname, Wrapper wt) {
+        visitMethodInsn(Opcodes.INVOKEVIRTUAL,
+                sname,
+                unboxMethod(wt),
+                unboxingDescriptor(wt));
+    }
+
+    private String descriptorToName(String desc) {
+        int last = desc.length() - 1;
+        if (desc.charAt(0) == 'L' && desc.charAt(last) == ';') {
+            // In descriptor form
+            return desc.substring(1, last);
+        } else {
+            // Already in internal name form
+            return desc;
+        }
+    }
+
+    void cast(String ds, String dt) {
+        String ns = descriptorToName(ds);
+        String nt = descriptorToName(dt);
+        if (!nt.equals(ns) && !nt.equals(NAME_OBJECT)) {
+            visitTypeInsn(Opcodes.CHECKCAST, nt);
+        }
+    }
+
+    private boolean isPrimitive(Wrapper w) {
+        return w != OBJECT;
+    }
+
+    private Wrapper toWrapper(String desc) {
+        char first = desc.charAt(0);
+        if (first == '[' || first == '(') {
+            first = 'L';
+        }
+        return Wrapper.forBasicType(first);
+    }
+
+    /**
+     * Convert an argument of type 'argType' to be passed to 'targetType' assuring that it is 'functionalType'.
+     * Insert the needed conversion instructions in the method code.
+     * @param argType
+     * @param targetType
+     * @param functionalType
+     */
+    void convertType(String dArg, String dTarget, String dFunctional) {
+        if (dArg.equals(dTarget)) {
+            return;
+        }
+        Wrapper wArg = toWrapper(dArg);
+        Wrapper wTarget = toWrapper(dTarget);
+        if (wArg == VOID || wTarget == VOID) {
+            return;
+        }
+        if (isPrimitive(wArg)) {
+            if (isPrimitive(wTarget)) {
+                // Both primitives: widening
+                widen(wArg, wTarget);
+            } else {
+                // Primitive argument to reference target
+                Wrapper wPrimTarget = wrapperOrNullFromDescriptor(dTarget);
+                if (wPrimTarget != null) {
+                    // The target is a boxed primitive type, widen to get there before boxing
+                    widen(wArg, wPrimTarget);
+                    box(wPrimTarget);
+                } else {
+                    // Otherwise, box and cast
+                    box(wArg);
+                    cast(wrapperName(wArg), dTarget);
+                }
+            }
+        } else {
+            String dSrc;
+            Wrapper wFunctional = toWrapper(dFunctional);
+            if (isPrimitive(wFunctional)) {
+                dSrc = dArg;
+            } else {
+                // Cast to convert to possibly more specific type, and generate CCE for invalid arg
+                dSrc = dFunctional;
+                cast(dArg, dFunctional);
+            }
+            if (isPrimitive(wTarget)) {
+                // Reference argument to primitive target
+                Wrapper wps = wrapperOrNullFromDescriptor(dSrc);
+                if (wps != null) {
+                    if (wps.isSigned() || wps.isFloating()) {
+                        // Boxed number to primitive
+                        unbox(wrapperName(wps), wTarget);
+                    } else {
+                        // Character or Boolean
+                        unbox(wrapperName(wps), wps);
+                        widen(wps, wTarget);
+                    }
+                } else {
+                    // Source type is reference type, but not boxed type,
+                    // assume it is super type of target type
+                    String intermediate;
+                    if (wTarget.isSigned() || wTarget.isFloating()) {
+                        // Boxed number to primitive
+                        intermediate = "java/lang/Number";
+                    } else {
+                        // Character or Boolean
+                        intermediate = wrapperName(wTarget);
+                    }
+                    cast(dSrc, intermediate);
+                    unbox(intermediate, wTarget);
+                }
+            } else {
+                // Both reference types: just case to target type
+                cast(dSrc, dTarget);
+            }
+        }
+    }
+}
--- a/src/share/classes/java/net/ProxySelector.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/net/ProxySelector.java	Mon Nov 05 10:33:18 2012 -0500
@@ -127,7 +127,6 @@
      * <UL>
      * <LI>http URI for http connections</LI>
      * <LI>https URI for https connections
-     * <LI>ftp URI for ftp connections</LI>
      * <LI><code>socket://host:port</code><br>
      *     for tcp client sockets connections</LI>
      * </UL>
--- a/src/share/classes/java/net/URL.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/net/URL.java	Mon Nov 05 10:33:18 2012 -0500
@@ -274,7 +274,7 @@
      * <p>Protocol handlers for the following protocols are guaranteed
      * to exist on the search path :-
      * <blockquote><pre>
-     *     http, https, ftp, file, and jar
+     *     http, https, file, and jar
      * </pre></blockquote>
      * Protocol handlers for additional protocols may also be
      * available.
--- a/src/share/classes/java/net/URLStreamHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/net/URLStreamHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -37,8 +37,7 @@
  * The abstract class <code>URLStreamHandler</code> is the common
  * superclass for all stream protocol handlers. A stream protocol
  * handler knows how to make a connection for a particular protocol
- * type, such as <code>http</code>, <code>ftp</code>, or
- * <code>gopher</code>.
+ * type, such as <code>http</code> or <code>https</code>.
  * <p>
  * In most cases, an instance of a <code>URLStreamHandler</code>
  * subclass is not created directly by an application. Rather, the
--- a/src/share/classes/java/net/package.html	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/net/package.html	Mon Nov 05 10:33:18 2012 -0500
@@ -72,7 +72,7 @@
 <ul>
       <li>{@link java.net.URI} is the class representing a Universal Resource Identifier, as specified in RFC 2396. As the name indicates, this is just an Identifier and doesn't provide directly the means to access the resource.</li>
       <li>{@link java.net.URL} is the class representing a Universal Resource Locator, which is both an older concept for URIs and a means to access the resources.</li>
-      <li>{@link java.net.URLConnection} is created from a URL and is the communication link used to access the resource pointed by the URL. This abstract class will delegate most of the work to the underlying protocol handlers like http or ftp.</li>
+      <li>{@link java.net.URLConnection} is created from a URL and is the communication link used to access the resource pointed by the URL. This abstract class will delegate most of the work to the underlying protocol handlers like http or https.</li>
       <li>{@link java.net.HttpURLConnection} is a subclass of URLConnection and provides some additional functionalities specific to the HTTP protocol.</li>
 </ul>
 <p>The recommended usage is to use {@link java.net.URI} to identify resources, then convert it into a {@link java.net.URL} when it is time to access the resource. From that URL, you can either get the {@link java.net.URLConnection} for fine control, or get directly the InputStream.<p>
--- a/src/share/classes/java/nio/file/Path.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/nio/file/Path.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2007, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2007, 2012, 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
@@ -297,7 +297,7 @@
      * @param   other
      *          the given path string
      *
-     * @return  {@code true} if this path starts with the given path; otherwise
+     * @return  {@code true} if this path ends with the given path; otherwise
      *          {@code false}
      *
      * @throws  InvalidPathException
--- a/src/share/classes/java/security/AccessController.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/security/AccessController.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2012, 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
@@ -290,11 +290,11 @@
      */
     public static <T> T doPrivilegedWithCombiner(PrivilegedAction<T> action) {
 
-        DomainCombiner dc = null;
         AccessControlContext acc = getStackAccessControlContext();
-        if (acc == null || (dc = acc.getAssignedCombiner()) == null) {
+        if (acc == null) {
             return AccessController.doPrivileged(action);
         }
+        DomainCombiner dc = acc.getAssignedCombiner();
         return AccessController.doPrivileged(action, preserveCombiner(dc));
     }
 
@@ -386,11 +386,11 @@
     public static <T> T doPrivilegedWithCombiner
         (PrivilegedExceptionAction<T> action) throws PrivilegedActionException {
 
-        DomainCombiner dc = null;
         AccessControlContext acc = getStackAccessControlContext();
-        if (acc == null || (dc = acc.getAssignedCombiner()) == null) {
+        if (acc == null) {
             return AccessController.doPrivileged(action);
         }
+        DomainCombiner dc = acc.getAssignedCombiner();
         return AccessController.doPrivileged(action, preserveCombiner(dc));
     }
 
@@ -417,7 +417,12 @@
         // perform 'combine' on the caller of doPrivileged,
         // even if the caller is from the bootclasspath
         ProtectionDomain[] pds = new ProtectionDomain[] {callerPd};
-        return new AccessControlContext(combiner.combine(pds, null), combiner);
+        if (combiner == null) {
+            return new AccessControlContext(pds);
+        } else {
+            return new AccessControlContext(combiner.combine(pds, null),
+                                            combiner);
+        }
     }
 
 
--- a/src/share/classes/java/util/ServiceLoader.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/ServiceLoader.java	Mon Nov 05 10:33:18 2012 -0500
@@ -358,14 +358,21 @@
             }
             String cn = nextName;
             nextName = null;
+            Class<?> c = null;
             try {
-                S p = service.cast(Class.forName(cn, true, loader)
-                                   .newInstance());
-                providers.put(cn, p);
-                return p;
+                c = Class.forName(cn, false, loader);
             } catch (ClassNotFoundException x) {
                 fail(service,
                      "Provider " + cn + " not found");
+            }
+            if (!service.isAssignableFrom(c)) {
+                fail(service,
+                     "Provider " + cn  + " not a subtype");
+            }
+            try {
+                S p = service.cast(c.newInstance());
+                providers.put(cn, p);
+                return p;
             } catch (Throwable x) {
                 fail(service,
                      "Provider " + cn + " could not be instantiated: " + x,
--- a/src/share/classes/java/util/concurrent/AbstractExecutorService.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/AbstractExecutorService.java	Mon Nov 05 10:33:18 2012 -0500
@@ -137,7 +137,7 @@
      * the main mechanics of invokeAny.
      */
     private <T> T doInvokeAny(Collection<? extends Callable<T>> tasks,
-                            boolean timed, long nanos)
+                              boolean timed, long nanos)
         throws InterruptedException, ExecutionException, TimeoutException {
         if (tasks == null)
             throw new NullPointerException();
@@ -158,7 +158,7 @@
             // Record exceptions so that if we fail to obtain any
             // result, we can throw the last exception we got.
             ExecutionException ee = null;
-            long lastTime = timed ? System.nanoTime() : 0;
+            final long deadline = timed ? System.nanoTime() + nanos : 0L;
             Iterator<? extends Callable<T>> it = tasks.iterator();
 
             // Start one task for sure; the rest incrementally
@@ -180,9 +180,7 @@
                         f = ecs.poll(nanos, TimeUnit.NANOSECONDS);
                         if (f == null)
                             throw new TimeoutException();
-                        long now = System.nanoTime();
-                        nanos -= now - lastTime;
-                        lastTime = now;
+                        nanos = deadline - System.nanoTime();
                     }
                     else
                         f = ecs.take();
@@ -258,7 +256,7 @@
     public <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks,
                                          long timeout, TimeUnit unit)
         throws InterruptedException {
-        if (tasks == null || unit == null)
+        if (tasks == null)
             throw new NullPointerException();
         long nanos = unit.toNanos(timeout);
         List<Future<T>> futures = new ArrayList<Future<T>>(tasks.size());
@@ -267,23 +265,21 @@
             for (Callable<T> t : tasks)
                 futures.add(newTaskFor(t));
 
-            long lastTime = System.nanoTime();
+            final long deadline = System.nanoTime() + nanos;
 
             // Interleave time checks and calls to execute in case
             // executor doesn't have any/much parallelism.
             Iterator<Future<T>> it = futures.iterator();
             while (it.hasNext()) {
                 execute((Runnable)(it.next()));
-                long now = System.nanoTime();
-                nanos -= now - lastTime;
-                lastTime = now;
-                if (nanos <= 0)
+                nanos = deadline - System.nanoTime();
+                if (nanos <= 0L)
                     return futures;
             }
 
             for (Future<T> f : futures) {
                 if (!f.isDone()) {
-                    if (nanos <= 0)
+                    if (nanos <= 0L)
                         return futures;
                     try {
                         f.get(nanos, TimeUnit.NANOSECONDS);
@@ -292,9 +288,7 @@
                     } catch (TimeoutException toe) {
                         return futures;
                     }
-                    long now = System.nanoTime();
-                    nanos -= now - lastTime;
-                    lastTime = now;
+                    nanos = deadline - System.nanoTime();
                 }
             }
             done = true;
--- a/src/share/classes/java/util/concurrent/BlockingQueue.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/BlockingQueue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -127,7 +127,7 @@
  * Usage example, based on a typical producer-consumer scenario.
  * Note that a <tt>BlockingQueue</tt> can safely be used with multiple
  * producers and multiple consumers.
- * <pre>
+ *  <pre> {@code
  * class Producer implements Runnable {
  *   private final BlockingQueue queue;
  *   Producer(BlockingQueue q) { queue = q; }
@@ -160,8 +160,7 @@
  *     new Thread(c1).start();
  *     new Thread(c2).start();
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
  * <p>Memory consistency effects: As with other concurrent
  * collections, actions in a thread prior to placing an object into a
--- a/src/share/classes/java/util/concurrent/BrokenBarrierException.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/BrokenBarrierException.java	Mon Nov 05 10:33:18 2012 -0500
@@ -44,7 +44,6 @@
  *
  * @since 1.5
  * @author Doug Lea
- *
  */
 public class BrokenBarrierException extends Exception {
     private static final long serialVersionUID = 7117394618823254244L;
--- a/src/share/classes/java/util/concurrent/CompletionService.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/CompletionService.java	Mon Nov 05 10:33:18 2012 -0500
@@ -57,7 +57,6 @@
  * <a href="package-summary.html#MemoryVisibility"><i>happen-before</i></a>
  * actions taken by that task, which in turn <i>happen-before</i>
  * actions following a successful return from the corresponding {@code take()}.
- *
  */
 public interface CompletionService<V> {
     /**
@@ -98,7 +97,6 @@
      */
     Future<V> take() throws InterruptedException;
 
-
     /**
      * Retrieves and removes the Future representing the next
      * completed task or <tt>null</tt> if none are present.
--- a/src/share/classes/java/util/concurrent/ConcurrentLinkedDeque.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ConcurrentLinkedDeque.java	Mon Nov 05 10:33:18 2012 -0500
@@ -90,7 +90,6 @@
  * @author Martin Buchholz
  * @param <E> the type of elements held in this collection
  */
-
 public class ConcurrentLinkedDeque<E>
     extends AbstractCollection<E>
     implements Deque<E>, java.io.Serializable {
@@ -1250,8 +1249,7 @@
      * The following code can be used to dump the deque into a newly
      * allocated array of {@code String}:
      *
-     * <pre>
-     *     String[] y = x.toArray(new String[0]);</pre>
+     *  <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
      *
      * Note that {@code toArray(new Object[0])} is identical in function to
      * {@code toArray()}.
@@ -1388,11 +1386,10 @@
     }
 
     /**
-     * Saves the state to a stream (that is, serializes it).
+     * Saves this deque to a stream (that is, serializes it).
      *
      * @serialData All of the elements (each an {@code E}) in
      * the proper order, followed by a null
-     * @param s the stream
      */
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
@@ -1412,8 +1409,7 @@
     }
 
     /**
-     * Reconstitutes the instance from a stream (that is, deserializes it).
-     * @param s the stream
+     * Reconstitutes this deque from a stream (that is, deserializes it).
      */
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
@@ -1436,7 +1432,6 @@
         initHeadTail(h, t);
     }
 
-
     private boolean casHead(Node<E> cmp, Node<E> val) {
         return UNSAFE.compareAndSwapObject(this, headOffset, cmp, val);
     }
--- a/src/share/classes/java/util/concurrent/ConcurrentLinkedQueue.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ConcurrentLinkedQueue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -98,7 +98,6 @@
  * @since 1.5
  * @author Doug Lea
  * @param <E> the type of elements held in this collection
- *
  */
 public class ConcurrentLinkedQueue<E> extends AbstractQueue<E>
         implements Queue<E>, java.io.Serializable {
@@ -247,7 +246,6 @@
      */
     private transient volatile Node<E> tail;
 
-
     /**
      * Creates a {@code ConcurrentLinkedQueue} that is initially empty.
      */
@@ -609,8 +607,7 @@
      * The following code can be used to dump the queue into a newly
      * allocated array of {@code String}:
      *
-     * <pre>
-     *     String[] y = x.toArray(new String[0]);</pre>
+     *  <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
      *
      * Note that {@code toArray(new Object[0])} is identical in function to
      * {@code toArray()}.
@@ -747,11 +744,10 @@
     }
 
     /**
-     * Saves the state to a stream (that is, serializes it).
+     * Saves this queue to a stream (that is, serializes it).
      *
      * @serialData All of the elements (each an {@code E}) in
      * the proper order, followed by a null
-     * @param s the stream
      */
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
@@ -771,8 +767,7 @@
     }
 
     /**
-     * Reconstitutes the instance from a stream (that is, deserializes it).
-     * @param s the stream
+     * Reconstitutes this queue from a stream (that is, deserializes it).
      */
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
--- a/src/share/classes/java/util/concurrent/ConcurrentMap.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ConcurrentMap.java	Mon Nov 05 10:33:18 2012 -0500
@@ -61,11 +61,12 @@
      * If the specified key is not already associated
      * with a value, associate it with the given value.
      * This is equivalent to
-     * <pre>
-     *   if (!map.containsKey(key))
-     *       return map.put(key, value);
-     *   else
-     *       return map.get(key);</pre>
+     *  <pre> {@code
+     * if (!map.containsKey(key))
+     *   return map.put(key, value);
+     * else
+     *   return map.get(key);}</pre>
+     *
      * except that the action is performed atomically.
      *
      * @param key key with which the specified value is to be associated
@@ -83,18 +84,19 @@
      *         and this map does not permit null keys or values
      * @throws IllegalArgumentException if some property of the specified key
      *         or value prevents it from being stored in this map
-     *
      */
     V putIfAbsent(K key, V value);
 
     /**
      * Removes the entry for a key only if currently mapped to a given value.
      * This is equivalent to
-     * <pre>
-     *   if (map.containsKey(key) &amp;&amp; map.get(key).equals(value)) {
-     *       map.remove(key);
-     *       return true;
-     *   } else return false;</pre>
+     *  <pre> {@code
+     * if (map.containsKey(key) && map.get(key).equals(value)) {
+     *   map.remove(key);
+     *   return true;
+     * } else
+     *   return false;}</pre>
+     *
      * except that the action is performed atomically.
      *
      * @param key key with which the specified value is associated
@@ -114,11 +116,13 @@
     /**
      * Replaces the entry for a key only if currently mapped to a given value.
      * This is equivalent to
-     * <pre>
-     *   if (map.containsKey(key) &amp;&amp; map.get(key).equals(oldValue)) {
-     *       map.put(key, newValue);
-     *       return true;
-     *   } else return false;</pre>
+     *  <pre> {@code
+     * if (map.containsKey(key) && map.get(key).equals(oldValue)) {
+     *   map.put(key, newValue);
+     *   return true;
+     * } else
+     *   return false;}</pre>
+     *
      * except that the action is performed atomically.
      *
      * @param key key with which the specified value is associated
@@ -139,10 +143,12 @@
     /**
      * Replaces the entry for a key only if currently mapped to some value.
      * This is equivalent to
-     * <pre>
-     *   if (map.containsKey(key)) {
-     *       return map.put(key, value);
-     *   } else return null;</pre>
+     *  <pre> {@code
+     * if (map.containsKey(key)) {
+     *   return map.put(key, value);
+     * } else
+     *   return null;}</pre>
+     *
      * except that the action is performed atomically.
      *
      * @param key key with which the specified value is associated
--- a/src/share/classes/java/util/concurrent/ConcurrentNavigableMap.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ConcurrentNavigableMap.java	Mon Nov 05 10:33:18 2012 -0500
@@ -67,7 +67,6 @@
      */
     ConcurrentNavigableMap<K,V> headMap(K toKey, boolean inclusive);
 
-
     /**
      * @throws ClassCastException       {@inheritDoc}
      * @throws NullPointerException     {@inheritDoc}
--- a/src/share/classes/java/util/concurrent/ConcurrentSkipListMap.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ConcurrentSkipListMap.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1507,7 +1507,7 @@
     /* ---------------- Serialization -------------- */
 
     /**
-     * Saves the state of this map to a stream (that is, serializes it).
+     * Saves this map to a stream (that is, serializes it).
      *
      * @serialData The key (Object) and value (Object) for each
      * key-value mapping represented by the map, followed by
@@ -1532,9 +1532,7 @@
     }
 
     /**
-     * Reconstitutes the map from a stream (that is, deserializes it).
-     *
-     * @param s the stream
+     * Reconstitutes this map from a stream (that is, deserializes it).
      */
     private void readObject(final java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
@@ -2342,7 +2340,7 @@
             Collection<?> c = (Collection<?>) o;
             try {
                 return containsAll(c) && c.containsAll(this);
-            } catch (ClassCastException unused)   {
+            } catch (ClassCastException unused) {
                 return false;
             } catch (NullPointerException unused) {
                 return false;
@@ -2451,7 +2449,7 @@
             Collection<?> c = (Collection<?>) o;
             try {
                 return containsAll(c) && c.containsAll(this);
-            } catch (ClassCastException unused)   {
+            } catch (ClassCastException unused) {
                 return false;
             } catch (NullPointerException unused) {
                 return false;
--- a/src/share/classes/java/util/concurrent/ConcurrentSkipListSet.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ConcurrentSkipListSet.java	Mon Nov 05 10:33:18 2012 -0500
@@ -298,7 +298,7 @@
         Collection<?> c = (Collection<?>) o;
         try {
             return containsAll(c) && c.containsAll(this);
-        } catch (ClassCastException unused)   {
+        } catch (ClassCastException unused) {
             return false;
         } catch (NullPointerException unused) {
             return false;
--- a/src/share/classes/java/util/concurrent/CopyOnWriteArrayList.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/CopyOnWriteArrayList.java	Mon Nov 05 10:33:18 2012 -0500
@@ -35,7 +35,7 @@
 
 package java.util.concurrent;
 import java.util.*;
-import java.util.concurrent.locks.*;
+import java.util.concurrent.locks.ReentrantLock;
 
 /**
  * A thread-safe variant of {@link java.util.ArrayList} in which all mutative
@@ -152,7 +152,7 @@
     }
 
     /**
-     * Test for equality, coping with nulls.
+     * Tests for equality, coping with nulls.
      */
     private static boolean eq(Object o1, Object o2) {
         return (o1 == null ? o2 == null : o1.equals(o2));
@@ -333,8 +333,7 @@
      * The following code can be used to dump the list into a newly
      * allocated array of <tt>String</tt>:
      *
-     * <pre>
-     *     String[] y = x.toArray(new String[0]);</pre>
+     *  <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
      *
      * Note that <tt>toArray(new Object[0])</tt> is identical in function to
      * <tt>toArray()</tt>.
@@ -548,9 +547,9 @@
      * @param fromIndex index of first element to be removed
      * @param toIndex index after last element to be removed
      * @throws IndexOutOfBoundsException if fromIndex or toIndex out of range
-     *         ({@code{fromIndex < 0 || toIndex > size() || toIndex < fromIndex})
+     *         ({@code fromIndex < 0 || toIndex > size() || toIndex < fromIndex})
      */
-    private void removeRange(int fromIndex, int toIndex) {
+    void removeRange(int fromIndex, int toIndex) {
         final ReentrantLock lock = this.lock;
         lock.lock();
         try {
@@ -576,7 +575,7 @@
     }
 
     /**
-     * Append the element if not present.
+     * Appends the element, if not present.
      *
      * @param e element to be added to this list, if absent
      * @return <tt>true</tt> if the element was added
@@ -641,6 +640,7 @@
      * @see #remove(Object)
      */
     public boolean removeAll(Collection<?> c) {
+        if (c == null) throw new NullPointerException();
         final ReentrantLock lock = this.lock;
         lock.lock();
         try {
@@ -683,6 +683,7 @@
      * @see #remove(Object)
      */
     public boolean retainAll(Collection<?> c) {
+        if (c == null) throw new NullPointerException();
         final ReentrantLock lock = this.lock;
         lock.lock();
         try {
@@ -837,15 +838,14 @@
     }
 
     /**
-     * Saves the state of the list to a stream (that is, serializes it).
+     * Saves this list to a stream (that is, serializes it).
      *
      * @serialData The length of the array backing the list is emitted
      *               (int), followed by all of its elements (each an Object)
      *               in the proper order.
-     * @param s the stream
      */
     private void writeObject(java.io.ObjectOutputStream s)
-        throws java.io.IOException{
+        throws java.io.IOException {
 
         s.defaultWriteObject();
 
@@ -859,9 +859,7 @@
     }
 
     /**
-     * Reconstitutes the list from a stream (that is, deserializes it).
-     *
-     * @param s the stream
+     * Reconstitutes this list from a stream (that is, deserializes it).
      */
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
@@ -1266,17 +1264,14 @@
 
 
     private static class COWSubListIterator<E> implements ListIterator<E> {
-        private final ListIterator<E> i;
-        private final int index;
+        private final ListIterator<E> it;
         private final int offset;
         private final int size;
 
-        COWSubListIterator(List<E> l, int index, int offset,
-                           int size) {
-            this.index = index;
+        COWSubListIterator(List<E> l, int index, int offset, int size) {
             this.offset = offset;
             this.size = size;
-            i = l.listIterator(index+offset);
+            it = l.listIterator(index+offset);
         }
 
         public boolean hasNext() {
@@ -1285,7 +1280,7 @@
 
         public E next() {
             if (hasNext())
-                return i.next();
+                return it.next();
             else
                 throw new NoSuchElementException();
         }
@@ -1296,17 +1291,17 @@
 
         public E previous() {
             if (hasPrevious())
-                return i.previous();
+                return it.previous();
             else
                 throw new NoSuchElementException();
         }
 
         public int nextIndex() {
-            return i.nextIndex() - offset;
+            return it.nextIndex() - offset;
         }
 
         public int previousIndex() {
-            return i.previousIndex() - offset;
+            return it.previousIndex() - offset;
         }
 
         public void remove() {
--- a/src/share/classes/java/util/concurrent/CopyOnWriteArraySet.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/CopyOnWriteArraySet.java	Mon Nov 05 10:33:18 2012 -0500
@@ -189,8 +189,7 @@
      * The following code can be used to dump the set into a newly allocated
      * array of <tt>String</tt>:
      *
-     * <pre>
-     *     String[] y = x.toArray(new String[0]);</pre>
+     *  <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
      *
      * Note that <tt>toArray(new Object[0])</tt> is identical in function to
      * <tt>toArray()</tt>.
@@ -384,9 +383,9 @@
     }
 
     /**
-     * Test for equality, coping with nulls.
+     * Tests for equality, coping with nulls.
      */
     private static boolean eq(Object o1, Object o2) {
-        return (o1 == null ? o2 == null : o1.equals(o2));
+        return (o1 == null) ? o2 == null : o1.equals(o2);
     }
 }
--- a/src/share/classes/java/util/concurrent/CountDownLatch.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/CountDownLatch.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,8 +34,7 @@
  */
 
 package java.util.concurrent;
-import java.util.concurrent.locks.*;
-import java.util.concurrent.atomic.*;
+import java.util.concurrent.locks.AbstractQueuedSynchronizer;
 
 /**
  * A synchronization aid that allows one or more threads to wait until
@@ -73,7 +72,7 @@
  * until all workers have completed.
  * </ul>
  *
- * <pre>
+ *  <pre> {@code
  * class Driver { // ...
  *   void main() throws InterruptedException {
  *     CountDownLatch startSignal = new CountDownLatch(1);
@@ -105,9 +104,7 @@
  *   }
  *
  *   void doWork() { ... }
- * }
- *
- * </pre>
+ * }}</pre>
  *
  * <p>Another typical usage would be to divide a problem into N parts,
  * describe each part with a Runnable that executes that portion and
@@ -116,7 +113,7 @@
  * will be able to pass through await. (When threads must repeatedly
  * count down in this way, instead use a {@link CyclicBarrier}.)
  *
- * <pre>
+ *  <pre> {@code
  * class Driver2 { // ...
  *   void main() throws InterruptedException {
  *     CountDownLatch doneSignal = new CountDownLatch(N);
@@ -144,9 +141,7 @@
  *   }
  *
  *   void doWork() { ... }
- * }
- *
- * </pre>
+ * }}</pre>
  *
  * <p>Memory consistency effects: Until the count reaches
  * zero, actions in a thread prior to calling
--- a/src/share/classes/java/util/concurrent/CyclicBarrier.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/CyclicBarrier.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,7 +34,8 @@
  */
 
 package java.util.concurrent;
-import java.util.concurrent.locks.*;
+import java.util.concurrent.locks.Condition;
+import java.util.concurrent.locks.ReentrantLock;
 
 /**
  * A synchronization aid that allows a set of threads to all wait for
@@ -52,7 +53,8 @@
  *
  * <p><b>Sample usage:</b> Here is an example of
  *  using a barrier in a parallel decomposition design:
- * <pre>
+ *
+ *  <pre> {@code
  * class Solver {
  *   final int N;
  *   final float[][] data;
@@ -90,8 +92,8 @@
  *
  *     waitUntilDone();
  *   }
- * }
- * </pre>
+ * }}</pre>
+ *
  * Here, each worker thread processes a row of the matrix then waits at the
  * barrier until all rows have been processed. When all rows are processed
  * the supplied {@link Runnable} barrier action is executed and merges the
@@ -105,9 +107,10 @@
  * {@link #await} returns the arrival index of that thread at the barrier.
  * You can then choose which thread should execute the barrier action, for
  * example:
- * <pre>  if (barrier.await() == 0) {
- *     // log the completion of this iteration
- *   }</pre>
+ *  <pre> {@code
+ * if (barrier.await() == 0) {
+ *   // log the completion of this iteration
+ * }}</pre>
  *
  * <p>The <tt>CyclicBarrier</tt> uses an all-or-none breakage model
  * for failed synchronization attempts: If a thread leaves a barrier
@@ -204,21 +207,21 @@
                 throw new InterruptedException();
             }
 
-           int index = --count;
-           if (index == 0) {  // tripped
-               boolean ranAction = false;
-               try {
-                   final Runnable command = barrierCommand;
-                   if (command != null)
-                       command.run();
-                   ranAction = true;
-                   nextGeneration();
-                   return 0;
-               } finally {
-                   if (!ranAction)
-                       breakBarrier();
-               }
-           }
+            int index = --count;
+            if (index == 0) {  // tripped
+                boolean ranAction = false;
+                try {
+                    final Runnable command = barrierCommand;
+                    if (command != null)
+                        command.run();
+                    ranAction = true;
+                    nextGeneration();
+                    return 0;
+                } finally {
+                    if (!ranAction)
+                        breakBarrier();
+                }
+            }
 
             // loop until tripped, broken, interrupted, or timed out
             for (;;) {
@@ -354,7 +357,7 @@
         try {
             return dowait(false, 0L);
         } catch (TimeoutException toe) {
-            throw new Error(toe); // cannot happen;
+            throw new Error(toe); // cannot happen
         }
     }
 
--- a/src/share/classes/java/util/concurrent/Delayed.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/Delayed.java	Mon Nov 05 10:33:18 2012 -0500
@@ -35,8 +35,6 @@
 
 package java.util.concurrent;
 
-import java.util.*;
-
 /**
  * A mix-in style interface for marking objects that should be
  * acted upon after a given delay.
--- a/src/share/classes/java/util/concurrent/ExecutionException.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ExecutionException.java	Mon Nov 05 10:33:18 2012 -0500
@@ -79,11 +79,9 @@
 
     /**
      * Constructs an <tt>ExecutionException</tt> with the specified cause.
-     * The detail message is set to:
-     * <pre>
-     *  (cause == null ? null : cause.toString())</pre>
-     * (which typically contains the class and detail message of
-     * <tt>cause</tt>).
+     * The detail message is set to {@code (cause == null ? null :
+     * cause.toString())} (which typically contains the class and
+     * detail message of {@code cause}).
      *
      * @param  cause the cause (which is saved for later retrieval by the
      *         {@link #getCause()} method)
--- a/src/share/classes/java/util/concurrent/Executor.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/Executor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -56,23 +56,23 @@
  * executor can run the submitted task immediately in the caller's
  * thread:
  *
- * <pre>
+ *  <pre> {@code
  * class DirectExecutor implements Executor {
- *     public void execute(Runnable r) {
- *         r.run();
- *     }
- * }</pre>
+ *   public void execute(Runnable r) {
+ *     r.run();
+ *   }
+ * }}</pre>
  *
  * More typically, tasks are executed in some thread other
  * than the caller's thread.  The executor below spawns a new thread
  * for each task.
  *
- * <pre>
+ *  <pre> {@code
  * class ThreadPerTaskExecutor implements Executor {
- *     public void execute(Runnable r) {
- *         new Thread(r).start();
- *     }
- * }</pre>
+ *   public void execute(Runnable r) {
+ *     new Thread(r).start();
+ *   }
+ * }}</pre>
  *
  * Many <tt>Executor</tt> implementations impose some sort of
  * limitation on how and when tasks are scheduled.  The executor below
--- a/src/share/classes/java/util/concurrent/ExecutorService.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ExecutorService.java	Mon Nov 05 10:33:18 2012 -0500
@@ -36,8 +36,6 @@
 package java.util.concurrent;
 import java.util.List;
 import java.util.Collection;
-import java.security.PrivilegedAction;
-import java.security.PrivilegedExceptionAction;
 
 /**
  * An {@link Executor} that provides methods to manage termination and
@@ -73,7 +71,7 @@
  * pool service incoming requests. It uses the preconfigured {@link
  * Executors#newFixedThreadPool} factory method:
  *
- * <pre>
+ *  <pre> {@code
  * class NetworkService implements Runnable {
  *   private final ServerSocket serverSocket;
  *   private final ExecutorService pool;
@@ -101,14 +99,13 @@
  *   public void run() {
  *     // read and service request on socket
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
  * The following method shuts down an <tt>ExecutorService</tt> in two phases,
  * first by calling <tt>shutdown</tt> to reject incoming tasks, and then
  * calling <tt>shutdownNow</tt>, if necessary, to cancel any lingering tasks:
  *
- * <pre>
+ *  <pre> {@code
  * void shutdownAndAwaitTermination(ExecutorService pool) {
  *   pool.shutdown(); // Disable new tasks from being submitted
  *   try {
@@ -125,8 +122,7 @@
  *     // Preserve interrupt status
  *     Thread.currentThread().interrupt();
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
  * <p>Memory consistency effects: Actions in a thread prior to the
  * submission of a {@code Runnable} or {@code Callable} task to an
@@ -214,7 +210,6 @@
     boolean awaitTermination(long timeout, TimeUnit unit)
         throws InterruptedException;
 
-
     /**
      * Submits a value-returning task for execution and returns a
      * Future representing the pending results of the task. The
@@ -286,7 +281,6 @@
      * @throws RejectedExecutionException if any task cannot be
      *         scheduled for execution
      */
-
     <T> List<Future<T>> invokeAll(Collection<? extends Callable<T>> tasks)
         throws InterruptedException;
 
--- a/src/share/classes/java/util/concurrent/Executors.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/Executors.java	Mon Nov 05 10:33:18 2012 -0500
@@ -530,18 +530,17 @@
                 return AccessController.doPrivileged(
                     new PrivilegedExceptionAction<T>() {
                         public T run() throws Exception {
-                            ClassLoader savedcl = null;
                             Thread t = Thread.currentThread();
-                            try {
-                                ClassLoader cl = t.getContextClassLoader();
-                                if (ccl != cl) {
-                                    t.setContextClassLoader(ccl);
-                                    savedcl = cl;
+                            ClassLoader cl = t.getContextClassLoader();
+                            if (ccl == cl) {
+                                return task.call();
+                            } else {
+                                t.setContextClassLoader(ccl);
+                                try {
+                                    return task.call();
+                                } finally {
+                                    t.setContextClassLoader(cl);
                                 }
-                                return task.call();
-                            } finally {
-                                if (savedcl != null)
-                                    t.setContextClassLoader(savedcl);
                             }
                         }
                     }, acc);
@@ -686,16 +685,16 @@
             super(executor);
             e = executor;
         }
-        public ScheduledFuture<?> schedule(Runnable command, long delay,  TimeUnit unit) {
+        public ScheduledFuture<?> schedule(Runnable command, long delay, TimeUnit unit) {
             return e.schedule(command, delay, unit);
         }
         public <V> ScheduledFuture<V> schedule(Callable<V> callable, long delay, TimeUnit unit) {
             return e.schedule(callable, delay, unit);
         }
-        public ScheduledFuture<?> scheduleAtFixedRate(Runnable command, long initialDelay,  long period, TimeUnit unit) {
+        public ScheduledFuture<?> scheduleAtFixedRate(Runnable command, long initialDelay, long period, TimeUnit unit) {
             return e.scheduleAtFixedRate(command, initialDelay, period, unit);
         }
-        public ScheduledFuture<?> scheduleWithFixedDelay(Runnable command, long initialDelay,  long delay, TimeUnit unit) {
+        public ScheduledFuture<?> scheduleWithFixedDelay(Runnable command, long initialDelay, long delay, TimeUnit unit) {
             return e.scheduleWithFixedDelay(command, initialDelay, delay, unit);
         }
     }
--- a/src/share/classes/java/util/concurrent/Future.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/Future.java	Mon Nov 05 10:33:18 2012 -0500
@@ -76,12 +76,12 @@
  * implements <tt>Runnable</tt>, and so may be executed by an <tt>Executor</tt>.
  * For example, the above construction with <tt>submit</tt> could be replaced by:
  *  <pre> {@code
- *     FutureTask<String> future =
- *       new FutureTask<String>(new Callable<String>() {
- *         public String call() {
- *           return searcher.search(target);
- *       }});
- *     executor.execute(future);}</pre>
+ * FutureTask<String> future =
+ *   new FutureTask<String>(new Callable<String>() {
+ *     public String call() {
+ *       return searcher.search(target);
+ *   }});
+ * executor.execute(future);}</pre>
  *
  * <p>Memory consistency effects: Actions taken by the asynchronous computation
  * <a href="package-summary.html#MemoryVisibility"> <i>happen-before</i></a>
--- a/src/share/classes/java/util/concurrent/LinkedBlockingDeque.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/LinkedBlockingDeque.java	Mon Nov 05 10:33:18 2012 -0500
@@ -73,7 +73,7 @@
  */
 public class LinkedBlockingDeque<E>
     extends AbstractQueue<E>
-    implements BlockingDeque<E>,  java.io.Serializable {
+    implements BlockingDeque<E>, java.io.Serializable {
 
     /*
      * Implemented as a simple doubly-linked list protected by a
@@ -922,8 +922,7 @@
      * The following code can be used to dump the deque into a newly
      * allocated array of {@code String}:
      *
-     * <pre>
-     *     String[] y = x.toArray(new String[0]);</pre>
+     *  <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
      *
      * Note that {@code toArray(new Object[0])} is identical in function to
      * {@code toArray()}.
@@ -1045,7 +1044,7 @@
         /**
          * The next node to return in next()
          */
-         Node<E> next;
+        Node<E> next;
 
         /**
          * nextItem holds on to item fields because once we claim that
@@ -1153,11 +1152,10 @@
     }
 
     /**
-     * Save the state of this deque to a stream (that is, serialize it).
+     * Saves this deque to a stream (that is, serializes it).
      *
      * @serialData The capacity (int), followed by elements (each an
      * {@code Object}) in the proper order, followed by a null
-     * @param s the stream
      */
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
@@ -1177,9 +1175,7 @@
     }
 
     /**
-     * Reconstitute this deque from a stream (that is,
-     * deserialize it).
-     * @param s the stream
+     * Reconstitutes this deque from a stream (that is, deserializes it).
      */
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
--- a/src/share/classes/java/util/concurrent/LinkedBlockingQueue.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/LinkedBlockingQueue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -73,7 +73,6 @@
  * @since 1.5
  * @author Doug Lea
  * @param <E> the type of elements held in this collection
- *
  */
 public class LinkedBlockingQueue<E> extends AbstractQueue<E>
         implements BlockingQueue<E>, java.io.Serializable {
@@ -135,13 +134,13 @@
     private final int capacity;
 
     /** Current number of elements */
-    private final AtomicInteger count = new AtomicInteger(0);
+    private final AtomicInteger count = new AtomicInteger();
 
     /**
      * Head of linked list.
      * Invariant: head.item == null
      */
-    private transient Node<E> head;
+    transient Node<E> head;
 
     /**
      * Tail of linked list.
@@ -291,7 +290,6 @@
         }
     }
 
-
     // this doc comment is overridden to remove the reference to collections
     // greater in size than Integer.MAX_VALUE
     /**
@@ -430,7 +428,6 @@
         return c >= 0;
     }
 
-
     public E take() throws InterruptedException {
         E x;
         int c = -1;
@@ -630,8 +627,7 @@
      * The following code can be used to dump the queue into a newly
      * allocated array of {@code String}:
      *
-     * <pre>
-     *     String[] y = x.toArray(new String[0]);</pre>
+     *  <pre> {@code String[] y = x.toArray(new String[0]);}</pre>
      *
      * Note that {@code toArray(new Object[0])} is identical in function to
      * {@code toArray()}.
@@ -777,7 +773,7 @@
      * @return an iterator over the elements in this queue in proper sequence
      */
     public Iterator<E> iterator() {
-      return new Itr();
+        return new Itr();
     }
 
     private class Itr implements Iterator<E> {
@@ -860,12 +856,11 @@
     }
 
     /**
-     * Save the state to a stream (that is, serialize it).
+     * Saves this queue to a stream (that is, serializes it).
      *
      * @serialData The capacity is emitted (int), followed by all of
      * its elements (each an {@code Object}) in the proper order,
      * followed by a null
-     * @param s the stream
      */
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
@@ -887,10 +882,7 @@
     }
 
     /**
-     * Reconstitute this queue instance from a stream (that is,
-     * deserialize it).
-     *
-     * @param s the stream
+     * Reconstitutes this queue from a stream (that is, deserializes it).
      */
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
--- a/src/share/classes/java/util/concurrent/LinkedTransferQueue.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/LinkedTransferQueue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -695,7 +695,7 @@
      * @return matched item, or e if unmatched on interrupt or timeout
      */
     private E awaitMatch(Node s, Node pred, E e, boolean timed, long nanos) {
-        long lastTime = timed ? System.nanoTime() : 0L;
+        final long deadline = timed ? System.nanoTime() + nanos : 0L;
         Thread w = Thread.currentThread();
         int spins = -1; // initialized after first item and cancel checks
         ThreadLocalRandom randomYields = null; // bound if needed
@@ -726,10 +726,9 @@
                 s.waiter = w;                 // request unpark then recheck
             }
             else if (timed) {
-                long now = System.nanoTime();
-                if ((nanos -= now - lastTime) > 0)
+                nanos = deadline - System.nanoTime();
+                if (nanos > 0L)
                     LockSupport.parkNanos(this, nanos);
-                lastTime = now;
             }
             else {
                 LockSupport.park(this);
@@ -1294,11 +1293,10 @@
     }
 
     /**
-     * Saves the state to a stream (that is, serializes it).
+     * Saves this queue to a stream (that is, serializes it).
      *
      * @serialData All of the elements (each an {@code E}) in
      * the proper order, followed by a null
-     * @param s the stream
      */
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
@@ -1310,10 +1308,7 @@
     }
 
     /**
-     * Reconstitutes the Queue instance from a stream (that is,
-     * deserializes it).
-     *
-     * @param s the stream
+     * Reconstitutes this queue from a stream (that is, deserializes it).
      */
     private void readObject(java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
--- a/src/share/classes/java/util/concurrent/RecursiveAction.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/RecursiveAction.java	Mon Nov 05 10:33:18 2012 -0500
@@ -39,37 +39,49 @@
  * A recursive resultless {@link ForkJoinTask}.  This class
  * establishes conventions to parameterize resultless actions as
  * {@code Void} {@code ForkJoinTask}s. Because {@code null} is the
- * only valid value of type {@code Void}, methods such as join always
- * return {@code null} upon completion.
+ * only valid value of type {@code Void}, methods such as {@code join}
+ * always return {@code null} upon completion.
  *
- * <p><b>Sample Usages.</b> Here is a sketch of a ForkJoin sort that
- * sorts a given {@code long[]} array:
+ * <p><b>Sample Usages.</b> Here is a simple but complete ForkJoin
+ * sort that sorts a given {@code long[]} array:
  *
  *  <pre> {@code
- * class SortTask extends RecursiveAction {
- *   final long[] array; final int lo; final int hi;
+ * static class SortTask extends RecursiveAction {
+ *   final long[] array; final int lo, hi;
  *   SortTask(long[] array, int lo, int hi) {
  *     this.array = array; this.lo = lo; this.hi = hi;
  *   }
+ *   SortTask(long[] array) { this(array, 0, array.length); }
  *   protected void compute() {
  *     if (hi - lo < THRESHOLD)
- *       sequentiallySort(array, lo, hi);
+ *       sortSequentially(lo, hi);
  *     else {
  *       int mid = (lo + hi) >>> 1;
  *       invokeAll(new SortTask(array, lo, mid),
  *                 new SortTask(array, mid, hi));
- *       merge(array, lo, hi);
+ *       merge(lo, mid, hi);
  *     }
  *   }
+ *   // implementation details follow:
+ *   final static int THRESHOLD = 1000;
+ *   void sortSequentially(int lo, int hi) {
+ *     Arrays.sort(array, lo, hi);
+ *   }
+ *   void merge(int lo, int mid, int hi) {
+ *     long[] buf = Arrays.copyOfRange(array, lo, mid);
+ *     for (int i = 0, j = lo, k = mid; i < buf.length; j++)
+ *       array[j] = (k == hi || buf[i] < array[k]) ?
+ *         buf[i++] : array[k++];
+ *   }
  * }}</pre>
  *
  * You could then sort {@code anArray} by creating {@code new
- * SortTask(anArray, 0, anArray.length-1) } and invoking it in a
- * ForkJoinPool.  As a more concrete simple example, the following
- * task increments each element of an array:
+ * SortTask(anArray)} and invoking it in a ForkJoinPool.  As a more
+ * concrete simple example, the following task increments each element
+ * of an array:
  *  <pre> {@code
  * class IncrementTask extends RecursiveAction {
- *   final long[] array; final int lo; final int hi;
+ *   final long[] array; final int lo, hi;
  *   IncrementTask(long[] array, int lo, int hi) {
  *     this.array = array; this.lo = lo; this.hi = hi;
  *   }
--- a/src/share/classes/java/util/concurrent/RejectedExecutionException.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/RejectedExecutionException.java	Mon Nov 05 10:33:18 2012 -0500
@@ -78,8 +78,8 @@
 
     /**
      * Constructs a <tt>RejectedExecutionException</tt> with the
-     * specified cause.  The detail message is set to: <pre> (cause ==
-     * null ? null : cause.toString())</pre> (which typically contains
+     * specified cause.  The detail message is set to {@code (cause ==
+     * null ? null : cause.toString())} (which typically contains
      * the class and detail message of <tt>cause</tt>).
      *
      * @param  cause the cause (which is saved for later retrieval by the
--- a/src/share/classes/java/util/concurrent/ScheduledExecutorService.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ScheduledExecutorService.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,8 +34,6 @@
  */
 
 package java.util.concurrent;
-import java.util.concurrent.atomic.*;
-import java.util.*;
 
 /**
  * An {@link ExecutorService} that can schedule commands to run after a given
--- a/src/share/classes/java/util/concurrent/ScheduledThreadPoolExecutor.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ScheduledThreadPoolExecutor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -223,7 +223,7 @@
         }
 
         /**
-         * Creates a one-shot action with given nanoTime-based trigger.
+         * Creates a one-shot action with given nanoTime-based trigger time.
          */
         ScheduledFutureTask(Callable<V> callable, long ns) {
             super(callable);
@@ -237,7 +237,7 @@
         }
 
         public int compareTo(Delayed other) {
-            if (other == this) // compare zero ONLY if same object
+            if (other == this) // compare zero if same object
                 return 0;
             if (other instanceof ScheduledFutureTask) {
                 ScheduledFutureTask<?> x = (ScheduledFutureTask<?>)other;
@@ -251,9 +251,8 @@
                 else
                     return 1;
             }
-            long d = (getDelay(NANOSECONDS) -
-                      other.getDelay(NANOSECONDS));
-            return (d == 0) ? 0 : ((d < 0) ? -1 : 1);
+            long diff = getDelay(NANOSECONDS) - other.getDelay(NANOSECONDS);
+            return (diff < 0) ? -1 : (diff > 0) ? 1 : 0;
         }
 
         /**
@@ -862,7 +861,7 @@
         private final Condition available = lock.newCondition();
 
         /**
-         * Set f's heapIndex if it is a ScheduledFutureTask.
+         * Sets f's heapIndex if it is a ScheduledFutureTask.
          */
         private void setIndex(RunnableScheduledFuture<?> f, int idx) {
             if (f instanceof ScheduledFutureTask)
@@ -870,7 +869,7 @@
         }
 
         /**
-         * Sift element added at bottom up to its heap-ordered spot.
+         * Sifts element added at bottom up to its heap-ordered spot.
          * Call only when holding lock.
          */
         private void siftUp(int k, RunnableScheduledFuture<?> key) {
@@ -888,7 +887,7 @@
         }
 
         /**
-         * Sift element added at top down to its heap-ordered spot.
+         * Sifts element added at top down to its heap-ordered spot.
          * Call only when holding lock.
          */
         private void siftDown(int k, RunnableScheduledFuture<?> key) {
@@ -910,7 +909,7 @@
         }
 
         /**
-         * Resize the heap array.  Call only when holding lock.
+         * Resizes the heap array.  Call only when holding lock.
          */
         private void grow() {
             int oldCapacity = queue.length;
@@ -921,7 +920,7 @@
         }
 
         /**
-         * Find index of given object, or -1 if absent
+         * Finds index of given object, or -1 if absent.
          */
         private int indexOf(Object x) {
             if (x != null) {
@@ -1162,15 +1161,14 @@
         }
 
         /**
-         * Return and remove first element only if it is expired.
+         * Returns first element only if it is expired.
          * Used only by drainTo.  Call only when holding lock.
          */
-        private RunnableScheduledFuture<?> pollExpired() {
+        private RunnableScheduledFuture<?> peekExpired() {
             // assert lock.isHeldByCurrentThread();
             RunnableScheduledFuture<?> first = queue[0];
-            if (first == null || first.getDelay(NANOSECONDS) > 0)
-                return null;
-            return finishPoll(first);
+            return (first == null || first.getDelay(NANOSECONDS) > 0) ?
+                null : first;
         }
 
         public int drainTo(Collection<? super Runnable> c) {
@@ -1183,8 +1181,9 @@
             try {
                 RunnableScheduledFuture<?> first;
                 int n = 0;
-                while ((first = pollExpired()) != null) {
-                    c.add(first);
+                while ((first = peekExpired()) != null) {
+                    c.add(first);   // In this order, in case add() throws.
+                    finishPoll(first);
                     ++n;
                 }
                 return n;
@@ -1205,8 +1204,9 @@
             try {
                 RunnableScheduledFuture<?> first;
                 int n = 0;
-                while (n < maxElements && (first = pollExpired()) != null) {
-                    c.add(first);
+                while (n < maxElements && (first = peekExpired()) != null) {
+                    c.add(first);   // In this order, in case add() throws.
+                    finishPoll(first);
                     ++n;
                 }
                 return n;
--- a/src/share/classes/java/util/concurrent/Semaphore.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/Semaphore.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,9 +34,8 @@
  */
 
 package java.util.concurrent;
-import java.util.*;
-import java.util.concurrent.locks.*;
-import java.util.concurrent.atomic.*;
+import java.util.Collection;
+import java.util.concurrent.locks.AbstractQueuedSynchronizer;
 
 /**
  * A counting semaphore.  Conceptually, a semaphore maintains a set of
@@ -49,7 +48,7 @@
  * <p>Semaphores are often used to restrict the number of threads than can
  * access some (physical or logical) resource. For example, here is
  * a class that uses a semaphore to control access to a pool of items:
- * <pre>
+ *  <pre> {@code
  * class Pool {
  *   private static final int MAX_AVAILABLE = 100;
  *   private final Semaphore available = new Semaphore(MAX_AVAILABLE, true);
@@ -91,9 +90,7 @@
  *     }
  *     return false;
  *   }
- *
- * }
- * </pre>
+ * }}</pre>
  *
  * <p>Before obtaining an item each thread must acquire a permit from
  * the semaphore, guaranteeing that an item is available for use. When
@@ -111,7 +108,7 @@
  * exclusion lock.  This is more commonly known as a <em>binary
  * semaphore</em>, because it only has two states: one permit
  * available, or zero permits available.  When used in this way, the
- * binary semaphore has the property (unlike many {@link Lock}
+ * binary semaphore has the property (unlike many {@link java.util.concurrent.locks.Lock}
  * implementations), that the &quot;lock&quot; can be released by a
  * thread other than the owner (as semaphores have no notion of
  * ownership).  This can be useful in some specialized contexts, such
@@ -155,9 +152,7 @@
  *
  * @since 1.5
  * @author Doug Lea
- *
  */
-
 public class Semaphore implements java.io.Serializable {
     private static final long serialVersionUID = -3222578661600680210L;
     /** All mechanics via AbstractQueuedSynchronizer subclass */
@@ -493,7 +488,6 @@
      *
      * @param permits the number of permits to acquire
      * @throws IllegalArgumentException if {@code permits} is negative
-     *
      */
     public void acquireUninterruptibly(int permits) {
         if (permits < 0) throw new IllegalArgumentException();
--- a/src/share/classes/java/util/concurrent/SynchronousQueue.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/SynchronousQueue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -35,7 +35,8 @@
  */
 
 package java.util.concurrent;
-import java.util.concurrent.locks.*;
+import java.util.concurrent.locks.LockSupport;
+import java.util.concurrent.locks.ReentrantLock;
 import java.util.*;
 
 /**
@@ -222,7 +223,7 @@
         /** Node is fulfilling another unfulfilled DATA or REQUEST */
         static final int FULFILLING = 2;
 
-        /** Return true if m has fulfilling bit set */
+        /** Returns true if m has fulfilling bit set. */
         static boolean isFulfilling(int m) { return (m & FULFILLING) != 0; }
 
         /** Node class for TransferStacks. */
@@ -430,9 +431,8 @@
              * and don't wait at all, so are trapped in transfer
              * method rather than calling awaitFulfill.
              */
-            long lastTime = timed ? System.nanoTime() : 0;
+            final long deadline = timed ? System.nanoTime() + nanos : 0L;
             Thread w = Thread.currentThread();
-            SNode h = head;
             int spins = (shouldSpin(s) ?
                          (timed ? maxTimedSpins : maxUntimedSpins) : 0);
             for (;;) {
@@ -442,10 +442,8 @@
                 if (m != null)
                     return m;
                 if (timed) {
-                    long now = System.nanoTime();
-                    nanos -= now - lastTime;
-                    lastTime = now;
-                    if (nanos <= 0) {
+                    nanos = deadline - System.nanoTime();
+                    if (nanos <= 0L) {
                         s.tryCancel();
                         continue;
                     }
@@ -737,7 +735,7 @@
          */
         Object awaitFulfill(QNode s, E e, boolean timed, long nanos) {
             /* Same idea as TransferStack.awaitFulfill */
-            long lastTime = timed ? System.nanoTime() : 0;
+            final long deadline = timed ? System.nanoTime() + nanos : 0L;
             Thread w = Thread.currentThread();
             int spins = ((head.next == s) ?
                          (timed ? maxTimedSpins : maxUntimedSpins) : 0);
@@ -748,10 +746,8 @@
                 if (x != e)
                     return x;
                 if (timed) {
-                    long now = System.nanoTime();
-                    nanos -= now - lastTime;
-                    lastTime = now;
-                    if (nanos <= 0) {
+                    nanos = deadline - System.nanoTime();
+                    if (nanos <= 0L) {
                         s.tryCancel(e);
                         continue;
                     }
@@ -874,9 +870,9 @@
      * @throws InterruptedException {@inheritDoc}
      * @throws NullPointerException {@inheritDoc}
      */
-    public void put(E o) throws InterruptedException {
-        if (o == null) throw new NullPointerException();
-        if (transferer.transfer(o, false, 0) == null) {
+    public void put(E e) throws InterruptedException {
+        if (e == null) throw new NullPointerException();
+        if (transferer.transfer(e, false, 0) == null) {
             Thread.interrupted();
             throw new InterruptedException();
         }
@@ -891,10 +887,10 @@
      * @throws InterruptedException {@inheritDoc}
      * @throws NullPointerException {@inheritDoc}
      */
-    public boolean offer(E o, long timeout, TimeUnit unit)
+    public boolean offer(E e, long timeout, TimeUnit unit)
         throws InterruptedException {
-        if (o == null) throw new NullPointerException();
-        if (transferer.transfer(o, true, unit.toNanos(timeout)) != null)
+        if (e == null) throw new NullPointerException();
+        if (transferer.transfer(e, true, unit.toNanos(timeout)) != null)
             return true;
         if (!Thread.interrupted())
             return false;
@@ -1162,9 +1158,7 @@
     private WaitQueue waitingConsumers;
 
     /**
-     * Saves the state to a stream (that is, serializes it).
-     *
-     * @param s the stream
+     * Saves this queue to a stream (that is, serializes it).
      */
     private void writeObject(java.io.ObjectOutputStream s)
         throws java.io.IOException {
@@ -1182,6 +1176,9 @@
         s.defaultWriteObject();
     }
 
+    /**
+     * Reconstitutes this queue from a stream (that is, deserializes it).
+     */
     private void readObject(final java.io.ObjectInputStream s)
         throws java.io.IOException, ClassNotFoundException {
         s.defaultReadObject();
--- a/src/share/classes/java/util/concurrent/ThreadFactory.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/ThreadFactory.java	Mon Nov 05 10:33:18 2012 -0500
@@ -42,13 +42,12 @@
  *
  * <p>
  * The simplest implementation of this interface is just:
- * <pre>
+ *  <pre> {@code
  * class SimpleThreadFactory implements ThreadFactory {
  *   public Thread newThread(Runnable r) {
  *     return new Thread(r);
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
  * The {@link Executors#defaultThreadFactory} method provides a more
  * useful simple implementation, that sets the created thread context
--- a/src/share/classes/java/util/concurrent/TimeUnit.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/TimeUnit.java	Mon Nov 05 10:33:18 2012 -0500
@@ -52,14 +52,14 @@
  * the following code will timeout in 50 milliseconds if the {@link
  * java.util.concurrent.locks.Lock lock} is not available:
  *
- * <pre>  Lock lock = ...;
- *  if (lock.tryLock(50L, TimeUnit.MILLISECONDS)) ...
- * </pre>
+ *  <pre> {@code
+ * Lock lock = ...;
+ * if (lock.tryLock(50L, TimeUnit.MILLISECONDS)) ...}</pre>
+ *
  * while this code will timeout in 50 seconds:
- * <pre>
- *  Lock lock = ...;
- *  if (lock.tryLock(50L, TimeUnit.SECONDS)) ...
- * </pre>
+ *  <pre> {@code
+ * Lock lock = ...;
+ * if (lock.tryLock(50L, TimeUnit.SECONDS)) ...}</pre>
  *
  * Note however, that there is no guarantee that a particular timeout
  * implementation will be able to notice the passage of time at the
--- a/src/share/classes/java/util/concurrent/atomic/AtomicInteger.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicInteger.java	Mon Nov 05 10:33:18 2012 -0500
@@ -245,7 +245,6 @@
         return Integer.toString(get());
     }
 
-
     /**
      * Returns the value of this {@code AtomicInteger} as an {@code int}.
      */
--- a/src/share/classes/java/util/concurrent/atomic/AtomicIntegerFieldUpdater.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicIntegerFieldUpdater.java	Mon Nov 05 10:33:18 2012 -0500
@@ -59,7 +59,7 @@
  * @author Doug Lea
  * @param <T> The type of the object holding the updatable field
  */
-public abstract class  AtomicIntegerFieldUpdater<T> {
+public abstract class AtomicIntegerFieldUpdater<T> {
     /**
      * Creates and returns an updater for objects with the given field.
      * The Class argument is needed to check that reflective types and
@@ -274,9 +274,9 @@
         private final Class<?> cclass;
 
         AtomicIntegerFieldUpdaterImpl(final Class<T> tclass, final String fieldName) {
-            Field field = null;
-            Class<?> caller = null;
-            int modifiers = 0;
+            final Field field;
+            final Class<?> caller;
+            final int modifiers;
             try {
                 field = AccessController.doPrivileged(
                     new PrivilegedExceptionAction<Field>() {
--- a/src/share/classes/java/util/concurrent/atomic/AtomicLong.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicLong.java	Mon Nov 05 10:33:18 2012 -0500
@@ -259,7 +259,6 @@
         return Long.toString(get());
     }
 
-
     /**
      * Returns the value of this {@code AtomicLong} as an {@code int}
      * after a narrowing primitive conversion.
--- a/src/share/classes/java/util/concurrent/atomic/AtomicLongFieldUpdater.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicLongFieldUpdater.java	Mon Nov 05 10:33:18 2012 -0500
@@ -59,7 +59,7 @@
  * @author Doug Lea
  * @param <T> The type of the object holding the updatable field
  */
-public abstract class  AtomicLongFieldUpdater<T> {
+public abstract class AtomicLongFieldUpdater<T> {
     /**
      * Creates and returns an updater for objects with the given field.
      * The Class argument is needed to check that reflective types and
@@ -274,9 +274,9 @@
         private final Class<?> cclass;
 
         CASUpdater(final Class<T> tclass, final String fieldName) {
-            Field field = null;
-            Class<?> caller = null;
-            int modifiers = 0;
+            final Field field;
+            final Class<?> caller;
+            final int modifiers;
             try {
                 field = AccessController.doPrivileged(
                     new PrivilegedExceptionAction<Field>() {
--- a/src/share/classes/java/util/concurrent/atomic/AtomicReference.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicReference.java	Mon Nov 05 10:33:18 2012 -0500
@@ -44,7 +44,7 @@
  * @author Doug Lea
  * @param <V> The type of object referred to by this reference
  */
-public class AtomicReference<V>  implements java.io.Serializable {
+public class AtomicReference<V> implements java.io.Serializable {
     private static final long serialVersionUID = -1848883965231344442L;
 
     private static final Unsafe unsafe = Unsafe.getUnsafe();
--- a/src/share/classes/java/util/concurrent/atomic/AtomicReferenceArray.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicReferenceArray.java	Mon Nov 05 10:33:18 2012 -0500
@@ -35,8 +35,8 @@
 
 package java.util.concurrent.atomic;
 
+import java.util.Arrays;
 import java.lang.reflect.Array;
-import java.util.Arrays;
 import sun.misc.Unsafe;
 
 /**
@@ -151,7 +151,6 @@
         unsafe.putOrderedObject(array, checkedByteOffset(i), newValue);
     }
 
-
     /**
      * Atomically sets the element at position {@code i} to the given
      * value and returns the old value.
@@ -225,10 +224,10 @@
 
     /**
      * Reconstitutes the instance from a stream (that is, deserializes it).
-     * @param s the stream
      */
     private void readObject(java.io.ObjectInputStream s)
-        throws java.io.IOException, ClassNotFoundException {
+        throws java.io.IOException, ClassNotFoundException,
+        java.io.InvalidObjectException {
         // Note: This must be changed if any additional fields are defined
         Object a = s.readFields().get("array", null);
         if (a == null || !a.getClass().isArray())
--- a/src/share/classes/java/util/concurrent/atomic/AtomicReferenceFieldUpdater.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/AtomicReferenceFieldUpdater.java	Mon Nov 05 10:33:18 2012 -0500
@@ -206,10 +206,10 @@
         AtomicReferenceFieldUpdaterImpl(final Class<T> tclass,
                                         Class<V> vclass,
                                         final String fieldName) {
-            Field field = null;
-            Class<?> fieldClass = null;
-            Class<?> caller = null;
-            int modifiers = 0;
+            final Field field;
+            final Class<?> fieldClass;
+            final Class<?> caller;
+            final int modifiers;
             try {
                 field = AccessController.doPrivileged(
                     new PrivilegedExceptionAction<Field>() {
@@ -220,12 +220,12 @@
                 caller = sun.reflect.Reflection.getCallerClass(3);
                 modifiers = field.getModifiers();
                 sun.reflect.misc.ReflectUtil.ensureMemberAccess(
-                                                                caller, tclass, null, modifiers);
+                    caller, tclass, null, modifiers);
                 ClassLoader cl = tclass.getClassLoader();
                 ClassLoader ccl = caller.getClassLoader();
                 if ((ccl != null) && (ccl != cl) &&
                     ((cl == null) || !isAncestor(cl, ccl))) {
-                    sun.reflect.misc.ReflectUtil.checkPackageAccess(tclass);
+                  sun.reflect.misc.ReflectUtil.checkPackageAccess(tclass);
                 }
                 fieldClass = field.getType();
             } catch (PrivilegedActionException pae) {
@@ -315,7 +315,7 @@
         }
 
         @SuppressWarnings("unchecked")
-            public V get(T obj) {
+        public V get(T obj) {
             if (obj == null || obj.getClass() != tclass || cclass != null)
                 targetCheck(obj);
             return (V)unsafe.getObjectVolatile(obj, offset);
@@ -326,14 +326,14 @@
                 return;
             }
             throw new RuntimeException(
-                                       new IllegalAccessException("Class " +
-                                                                  cclass.getName() +
-                                                                  " can not access a protected member of class " +
-                                                                  tclass.getName() +
-                                                                  " using an instance of " +
-                                                                  obj.getClass().getName()
-                                                                  )
-                                       );
+                new IllegalAccessException("Class " +
+                    cclass.getName() +
+                    " can not access a protected member of class " +
+                    tclass.getName() +
+                    " using an instance of " +
+                    obj.getClass().getName()
+                )
+            );
         }
     }
 }
--- a/src/share/classes/java/util/concurrent/atomic/package-info.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/atomic/package-info.java	Mon Nov 05 10:33:18 2012 -0500
@@ -40,9 +40,7 @@
  * array elements to those that also provide an atomic conditional update
  * operation of the form:
  *
- * <pre>
- *   boolean compareAndSet(expectedValue, updateValue);
- * </pre>
+ *  <pre> {@code boolean compareAndSet(expectedValue, updateValue);}</pre>
  *
  * <p>This method (which varies in argument types across different
  * classes) atomically sets a variable to the {@code updateValue} if it
@@ -69,19 +67,36 @@
  * {@code AtomicInteger} provide atomic increment methods.  One
  * application is to generate sequence numbers, as in:
  *
- * <pre>
+ *  <pre> {@code
  * class Sequencer {
  *   private final AtomicLong sequenceNumber
  *     = new AtomicLong(0);
  *   public long next() {
  *     return sequenceNumber.getAndIncrement();
  *   }
- * }
- * </pre>
+ * }}</pre>
+ *
+ * <p>It is straightforward to define new utility functions that, like
+ * {@code getAndIncrement}, apply a function to a value atomically.
+ * For example, given some transformation
+ * <pre> {@code long transform(long input)}</pre>
+ *
+ * write your utility method as follows:
+ *  <pre> {@code
+ * long getAndTransform(AtomicLong var) {
+ *   while (true) {
+ *     long current = var.get();
+ *     long next = transform(current);
+ *     if (var.compareAndSet(current, next))
+ *         return current;
+ *         // return next; for transformAndGet
+ *   }
+ * }}</pre>
  *
  * <p>The memory effects for accesses and updates of atomics generally
- * follow the rules for volatiles, as stated in section 17.4 of
- * <cite>The Java&trade; Language Specification</cite>.
+ * follow the rules for volatiles, as stated in
+ * <a href="http://docs.oracle.com/javase/specs/jls/se7/html/index.html">
+ * The Java Language Specification, Third Edition (17.4 Memory Model)</a>:
  *
  * <ul>
  *
@@ -189,9 +204,9 @@
  * {@code byte} values, and cast appropriately.
  *
  * You can also hold floats using
- * {@link java.lang.Float#floatToIntBits} and
+ * {@link java.lang.Float#floatToRawIntBits} and
  * {@link java.lang.Float#intBitsToFloat} conversions, and doubles using
- * {@link java.lang.Double#doubleToLongBits} and
+ * {@link java.lang.Double#doubleToRawLongBits} and
  * {@link java.lang.Double#longBitsToDouble} conversions.
  *
  * @since 1.5
--- a/src/share/classes/java/util/concurrent/locks/AbstractQueuedLongSynchronizer.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/AbstractQueuedLongSynchronizer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,9 +34,10 @@
  */
 
 package java.util.concurrent.locks;
-import java.util.*;
-import java.util.concurrent.*;
-import java.util.concurrent.atomic.*;
+import java.util.concurrent.TimeUnit;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
 import sun.misc.Unsafe;
 
 /**
@@ -598,7 +599,7 @@
     /**
      * Convenience method to interrupt current thread.
      */
-    private static void selfInterrupt() {
+    static void selfInterrupt() {
         Thread.currentThread().interrupt();
     }
 
@@ -686,8 +687,10 @@
      * @return {@code true} if acquired
      */
     private boolean doAcquireNanos(long arg, long nanosTimeout)
-        throws InterruptedException {
-        long lastTime = System.nanoTime();
+            throws InterruptedException {
+        if (nanosTimeout <= 0L)
+            return false;
+        final long deadline = System.nanoTime() + nanosTimeout;
         final Node node = addWaiter(Node.EXCLUSIVE);
         boolean failed = true;
         try {
@@ -699,14 +702,12 @@
                     failed = false;
                     return true;
                 }
-                if (nanosTimeout <= 0)
+                nanosTimeout = deadline - System.nanoTime();
+                if (nanosTimeout <= 0L)
                     return false;
                 if (shouldParkAfterFailedAcquire(p, node) &&
                     nanosTimeout > spinForTimeoutThreshold)
                     LockSupport.parkNanos(this, nanosTimeout);
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
                 if (Thread.interrupted())
                     throw new InterruptedException();
             }
@@ -786,9 +787,10 @@
      * @return {@code true} if acquired
      */
     private boolean doAcquireSharedNanos(long arg, long nanosTimeout)
-        throws InterruptedException {
-
-        long lastTime = System.nanoTime();
+            throws InterruptedException {
+        if (nanosTimeout <= 0L)
+            return false;
+        final long deadline = System.nanoTime() + nanosTimeout;
         final Node node = addWaiter(Node.SHARED);
         boolean failed = true;
         try {
@@ -803,14 +805,12 @@
                         return true;
                     }
                 }
-                if (nanosTimeout <= 0)
+                nanosTimeout = deadline - System.nanoTime();
+                if (nanosTimeout <= 0L)
                     return false;
                 if (shouldParkAfterFailedAcquire(p, node) &&
                     nanosTimeout > spinForTimeoutThreshold)
                     LockSupport.parkNanos(this, nanosTimeout);
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
                 if (Thread.interrupted())
                     throw new InterruptedException();
             }
@@ -1260,7 +1260,7 @@
      * due to the queue being empty.
      *
      * <p>This method is designed to be used by a fair synchronizer to
-     * avoid <a href="AbstractQueuedSynchronizer#barging">barging</a>.
+     * avoid <a href="AbstractQueuedSynchronizer.html#barging">barging</a>.
      * Such a synchronizer's {@link #tryAcquire} method should return
      * {@code false}, and its {@link #tryAcquireShared} method should
      * return a negative value, if this method returns {@code true}
@@ -1520,8 +1520,6 @@
      * @throws NullPointerException if the condition is null
      */
     public final boolean owns(ConditionObject condition) {
-        if (condition == null)
-            throw new NullPointerException();
         return condition.isOwnedBy(this);
     }
 
@@ -1742,9 +1740,8 @@
          * Implements uninterruptible condition wait.
          * <ol>
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -1803,9 +1800,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled or interrupted.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -1836,9 +1832,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled, interrupted, or timed out.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -1851,20 +1846,18 @@
                 throw new InterruptedException();
             Node node = addConditionWaiter();
             long savedState = fullyRelease(node);
-            long lastTime = System.nanoTime();
+            final long deadline = System.nanoTime() + nanosTimeout;
             int interruptMode = 0;
             while (!isOnSyncQueue(node)) {
                 if (nanosTimeout <= 0L) {
                     transferAfterCancelledWait(node);
                     break;
                 }
-                LockSupport.parkNanos(this, nanosTimeout);
+                if (nanosTimeout >= spinForTimeoutThreshold)
+                    LockSupport.parkNanos(this, nanosTimeout);
                 if ((interruptMode = checkInterruptWhileWaiting(node)) != 0)
                     break;
-
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
+                nanosTimeout = deadline - System.nanoTime();
             }
             if (acquireQueued(node, savedState) && interruptMode != THROW_IE)
                 interruptMode = REINTERRUPT;
@@ -1872,7 +1865,7 @@
                 unlinkCancelledWaiters();
             if (interruptMode != 0)
                 reportInterruptAfterWait(interruptMode);
-            return nanosTimeout - (System.nanoTime() - lastTime);
+            return deadline - System.nanoTime();
         }
 
         /**
@@ -1880,9 +1873,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled, interrupted, or timed out.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -1892,8 +1884,6 @@
          */
         public final boolean awaitUntil(Date deadline)
                 throws InterruptedException {
-            if (deadline == null)
-                throw new NullPointerException();
             long abstime = deadline.getTime();
             if (Thread.interrupted())
                 throw new InterruptedException();
@@ -1924,9 +1914,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled, interrupted, or timed out.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -1936,14 +1925,12 @@
          */
         public final boolean await(long time, TimeUnit unit)
                 throws InterruptedException {
-            if (unit == null)
-                throw new NullPointerException();
             long nanosTimeout = unit.toNanos(time);
             if (Thread.interrupted())
                 throw new InterruptedException();
             Node node = addConditionWaiter();
             long savedState = fullyRelease(node);
-            long lastTime = System.nanoTime();
+            final long deadline = System.nanoTime() + nanosTimeout;
             boolean timedout = false;
             int interruptMode = 0;
             while (!isOnSyncQueue(node)) {
@@ -1955,9 +1942,7 @@
                     LockSupport.parkNanos(this, nanosTimeout);
                 if ((interruptMode = checkInterruptWhileWaiting(node)) != 0)
                     break;
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
+                nanosTimeout = deadline - System.nanoTime();
             }
             if (acquireQueued(node, savedState) && interruptMode != THROW_IE)
                 interruptMode = REINTERRUPT;
--- a/src/share/classes/java/util/concurrent/locks/AbstractQueuedSynchronizer.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/AbstractQueuedSynchronizer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,9 +34,10 @@
  */
 
 package java.util.concurrent.locks;
-import java.util.*;
-import java.util.concurrent.*;
-import java.util.concurrent.atomic.*;
+import java.util.concurrent.TimeUnit;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
 import sun.misc.Unsafe;
 
 /**
@@ -194,7 +195,7 @@
  * It also supports conditions and exposes
  * one of the instrumentation methods:
  *
- * <pre>
+ *  <pre> {@code
  * class Mutex implements Lock, java.io.Serializable {
  *
  *   // Our internal helper class
@@ -250,15 +251,15 @@
  *       throws InterruptedException {
  *     return sync.tryAcquireNanos(1, unit.toNanos(timeout));
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
- * <p>Here is a latch class that is like a {@link CountDownLatch}
+ * <p>Here is a latch class that is like a
+ * {@link java.util.concurrent.CountDownLatch CountDownLatch}
  * except that it only requires a single <tt>signal</tt> to
  * fire. Because a latch is non-exclusive, it uses the <tt>shared</tt>
  * acquire and release methods.
  *
- * <pre>
+ *  <pre> {@code
  * class BooleanLatch {
  *
  *   private static class Sync extends AbstractQueuedSynchronizer {
@@ -280,8 +281,7 @@
  *   public void await() throws InterruptedException {
  *     sync.acquireSharedInterruptibly(1);
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
  * @since 1.5
  * @author Doug Lea
@@ -821,7 +821,7 @@
     /**
      * Convenience method to interrupt current thread.
      */
-    private static void selfInterrupt() {
+    static void selfInterrupt() {
         Thread.currentThread().interrupt();
     }
 
@@ -909,8 +909,10 @@
      * @return {@code true} if acquired
      */
     private boolean doAcquireNanos(int arg, long nanosTimeout)
-        throws InterruptedException {
-        long lastTime = System.nanoTime();
+            throws InterruptedException {
+        if (nanosTimeout <= 0L)
+            return false;
+        final long deadline = System.nanoTime() + nanosTimeout;
         final Node node = addWaiter(Node.EXCLUSIVE);
         boolean failed = true;
         try {
@@ -922,14 +924,12 @@
                     failed = false;
                     return true;
                 }
-                if (nanosTimeout <= 0)
+                nanosTimeout = deadline - System.nanoTime();
+                if (nanosTimeout <= 0L)
                     return false;
                 if (shouldParkAfterFailedAcquire(p, node) &&
                     nanosTimeout > spinForTimeoutThreshold)
                     LockSupport.parkNanos(this, nanosTimeout);
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
                 if (Thread.interrupted())
                     throw new InterruptedException();
             }
@@ -1009,9 +1009,10 @@
      * @return {@code true} if acquired
      */
     private boolean doAcquireSharedNanos(int arg, long nanosTimeout)
-        throws InterruptedException {
-
-        long lastTime = System.nanoTime();
+            throws InterruptedException {
+        if (nanosTimeout <= 0L)
+            return false;
+        final long deadline = System.nanoTime() + nanosTimeout;
         final Node node = addWaiter(Node.SHARED);
         boolean failed = true;
         try {
@@ -1026,14 +1027,12 @@
                         return true;
                     }
                 }
-                if (nanosTimeout <= 0)
+                nanosTimeout = deadline - System.nanoTime();
+                if (nanosTimeout <= 0L)
                     return false;
                 if (shouldParkAfterFailedAcquire(p, node) &&
                     nanosTimeout > spinForTimeoutThreshold)
                     LockSupport.parkNanos(this, nanosTimeout);
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
                 if (Thread.interrupted())
                     throw new InterruptedException();
             }
@@ -1743,8 +1742,6 @@
      * @throws NullPointerException if the condition is null
      */
     public final boolean owns(ConditionObject condition) {
-        if (condition == null)
-            throw new NullPointerException();
         return condition.isOwnedBy(this);
     }
 
@@ -1963,9 +1960,8 @@
          * Implements uninterruptible condition wait.
          * <ol>
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -2024,9 +2020,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled or interrupted.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -2057,9 +2052,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled, interrupted, or timed out.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -2072,20 +2066,18 @@
                 throw new InterruptedException();
             Node node = addConditionWaiter();
             int savedState = fullyRelease(node);
-            long lastTime = System.nanoTime();
+            final long deadline = System.nanoTime() + nanosTimeout;
             int interruptMode = 0;
             while (!isOnSyncQueue(node)) {
                 if (nanosTimeout <= 0L) {
                     transferAfterCancelledWait(node);
                     break;
                 }
-                LockSupport.parkNanos(this, nanosTimeout);
+                if (nanosTimeout >= spinForTimeoutThreshold)
+                    LockSupport.parkNanos(this, nanosTimeout);
                 if ((interruptMode = checkInterruptWhileWaiting(node)) != 0)
                     break;
-
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
+                nanosTimeout = deadline - System.nanoTime();
             }
             if (acquireQueued(node, savedState) && interruptMode != THROW_IE)
                 interruptMode = REINTERRUPT;
@@ -2093,7 +2085,7 @@
                 unlinkCancelledWaiters();
             if (interruptMode != 0)
                 reportInterruptAfterWait(interruptMode);
-            return nanosTimeout - (System.nanoTime() - lastTime);
+            return deadline - System.nanoTime();
         }
 
         /**
@@ -2101,9 +2093,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled, interrupted, or timed out.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -2113,8 +2104,6 @@
          */
         public final boolean awaitUntil(Date deadline)
                 throws InterruptedException {
-            if (deadline == null)
-                throw new NullPointerException();
             long abstime = deadline.getTime();
             if (Thread.interrupted())
                 throw new InterruptedException();
@@ -2145,9 +2134,8 @@
          * <ol>
          * <li> If current thread is interrupted, throw InterruptedException.
          * <li> Save lock state returned by {@link #getState}.
-         * <li> Invoke {@link #release} with
-         *      saved state as argument, throwing
-         *      IllegalMonitorStateException if it fails.
+         * <li> Invoke {@link #release} with saved state as argument,
+         *      throwing IllegalMonitorStateException if it fails.
          * <li> Block until signalled, interrupted, or timed out.
          * <li> Reacquire by invoking specialized version of
          *      {@link #acquire} with saved state as argument.
@@ -2157,14 +2145,12 @@
          */
         public final boolean await(long time, TimeUnit unit)
                 throws InterruptedException {
-            if (unit == null)
-                throw new NullPointerException();
             long nanosTimeout = unit.toNanos(time);
             if (Thread.interrupted())
                 throw new InterruptedException();
             Node node = addConditionWaiter();
             int savedState = fullyRelease(node);
-            long lastTime = System.nanoTime();
+            final long deadline = System.nanoTime() + nanosTimeout;
             boolean timedout = false;
             int interruptMode = 0;
             while (!isOnSyncQueue(node)) {
@@ -2176,9 +2162,7 @@
                     LockSupport.parkNanos(this, nanosTimeout);
                 if ((interruptMode = checkInterruptWhileWaiting(node)) != 0)
                     break;
-                long now = System.nanoTime();
-                nanosTimeout -= now - lastTime;
-                lastTime = now;
+                nanosTimeout = deadline - System.nanoTime();
             }
             if (acquireQueued(node, savedState) && interruptMode != THROW_IE)
                 interruptMode = REINTERRUPT;
--- a/src/share/classes/java/util/concurrent/locks/Condition.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/Condition.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,7 +34,7 @@
  */
 
 package java.util.concurrent.locks;
-import java.util.concurrent.*;
+import java.util.concurrent.TimeUnit;
 import java.util.Date;
 
 /**
@@ -360,10 +360,9 @@
     /**
      * Causes the current thread to wait until it is signalled or interrupted,
      * or the specified waiting time elapses. This method is behaviorally
-     * equivalent to:<br>
-     * <pre>
-     *   awaitNanos(unit.toNanos(time)) &gt; 0
-     * </pre>
+     * equivalent to:
+     *  <pre> {@code awaitNanos(unit.toNanos(time)) > 0}</pre>
+     *
      * @param time the maximum time to wait
      * @param unit the time unit of the {@code time} argument
      * @return {@code false} if the waiting time detectably elapsed
--- a/src/share/classes/java/util/concurrent/locks/Lock.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/Lock.java	Mon Nov 05 10:33:18 2012 -0500
@@ -77,14 +77,14 @@
  * methods and statements. In most cases, the following idiom
  * should be used:
  *
- * <pre><tt>     Lock l = ...;
- *     l.lock();
- *     try {
- *         // access the resource protected by this lock
- *     } finally {
- *         l.unlock();
- *     }
- * </tt></pre>
+ *  <pre> {@code
+ * Lock l = ...;
+ * l.lock();
+ * try {
+ *   // access the resource protected by this lock
+ * } finally {
+ *   l.unlock();
+ * }}</pre>
  *
  * When locking and unlocking occur in different scopes, care must be
  * taken to ensure that all code that is executed while the lock is
@@ -120,8 +120,9 @@
  *
  * <p>All {@code Lock} implementations <em>must</em> enforce the same
  * memory synchronization semantics as provided by the built-in monitor
- * lock, as described in section 17.4 of
- * <cite>The Java&trade; Language Specification</cite>:
+ * lock, as described in
+ * <a href="http://docs.oracle.com/javase/specs/jls/se7/html/index.html">
+ * The Java Language Specification, Third Edition (17.4 Memory Model)</a>:
  * <ul>
  * <li>A successful {@code lock} operation has the same memory
  * synchronization effects as a successful <em>Lock</em> action.
@@ -239,18 +240,18 @@
      * immediately with the value {@code false}.
      *
      * <p>A typical usage idiom for this method would be:
-     * <pre>
-     *      Lock lock = ...;
-     *      if (lock.tryLock()) {
-     *          try {
-     *              // manipulate protected state
-     *          } finally {
-     *              lock.unlock();
-     *          }
-     *      } else {
-     *          // perform alternative actions
-     *      }
-     * </pre>
+     *  <pre> {@code
+     * Lock lock = ...;
+     * if (lock.tryLock()) {
+     *   try {
+     *     // manipulate protected state
+     *   } finally {
+     *     lock.unlock();
+     *   }
+     * } else {
+     *   // perform alternative actions
+     * }}</pre>
+     *
      * This usage ensures that the lock is unlocked if it was acquired, and
      * doesn't try to unlock if the lock was not acquired.
      *
--- a/src/share/classes/java/util/concurrent/locks/LockSupport.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/LockSupport.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,10 +34,8 @@
  */
 
 package java.util.concurrent.locks;
-import java.util.concurrent.*;
 import sun.misc.Unsafe;
 
-
 /**
  * Basic thread blocking primitives for creating locks and other
  * synchronization classes.
@@ -78,7 +76,10 @@
  * higher-level synchronization utilities, and are not in themselves
  * useful for most concurrency control applications.  The {@code park}
  * method is designed for use only in constructions of the form:
- * <pre>while (!canProceed()) { ... LockSupport.park(this); }</pre>
+ *
+ *  <pre> {@code
+ * while (!canProceed()) { ... LockSupport.park(this); }}</pre>
+ *
  * where neither {@code canProceed} nor any other actions prior to the
  * call to {@code park} entail locking or blocking.  Because only one
  * permit is associated with each thread, any intermediary uses of
@@ -86,7 +87,7 @@
  *
  * <p><b>Sample Usage.</b> Here is a sketch of a first-in-first-out
  * non-reentrant lock class:
- * <pre>{@code
+ *  <pre> {@code
  * class FIFOMutex {
  *   private final AtomicBoolean locked = new AtomicBoolean(false);
  *   private final Queue<Thread> waiters
@@ -116,7 +117,6 @@
  *   }
  * }}</pre>
  */
-
 public class LockSupport {
     private LockSupport() {} // Cannot be instantiated.
 
--- a/src/share/classes/java/util/concurrent/locks/ReentrantLock.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/ReentrantLock.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,9 +34,8 @@
  */
 
 package java.util.concurrent.locks;
-import java.util.*;
-import java.util.concurrent.*;
-import java.util.concurrent.atomic.*;
+import java.util.concurrent.TimeUnit;
+import java.util.Collection;
 
 /**
  * A reentrant mutual exclusion {@link Lock} with the same basic
@@ -73,7 +72,7 @@
  * follow a call to {@code lock} with a {@code try} block, most
  * typically in a before/after construction such as:
  *
- * <pre>
+ *  <pre> {@code
  * class X {
  *   private final ReentrantLock lock = new ReentrantLock();
  *   // ...
@@ -86,8 +85,7 @@
  *       lock.unlock()
  *     }
  *   }
- * }
- * </pre>
+ * }}</pre>
  *
  * <p>In addition to implementing the {@link Lock} interface, this
  * class defines methods {@code isLocked} and
@@ -187,8 +185,7 @@
         }
 
         /**
-         * Reconstitutes this lock instance from a stream.
-         * @param s the stream
+         * Reconstitutes the instance from a stream (that is, deserializes it).
          */
         private void readObject(java.io.ObjectInputStream s)
             throws java.io.IOException, ClassNotFoundException {
@@ -383,8 +380,11 @@
      * method. If you want a timed {@code tryLock} that does permit barging on
      * a fair lock then combine the timed and un-timed forms together:
      *
-     * <pre>if (lock.tryLock() || lock.tryLock(timeout, unit) ) { ... }
-     * </pre>
+     *  <pre> {@code
+     * if (lock.tryLock() ||
+     *     lock.tryLock(timeout, unit)) {
+     *   ...
+     * }}</pre>
      *
      * <p>If the current thread
      * already holds this lock then the hold count is incremented by one and
@@ -438,7 +438,6 @@
      *         the lock could be acquired
      * @throws InterruptedException if the current thread is interrupted
      * @throws NullPointerException if the time unit is null
-     *
      */
     public boolean tryLock(long timeout, TimeUnit unit)
             throws InterruptedException {
@@ -514,7 +513,7 @@
      * not be entered with the lock already held then we can assert that
      * fact:
      *
-     * <pre>
+     *  <pre> {@code
      * class X {
      *   ReentrantLock lock = new ReentrantLock();
      *   // ...
@@ -527,8 +526,7 @@
      *       lock.unlock();
      *     }
      *   }
-     * }
-     * </pre>
+     * }}</pre>
      *
      * @return the number of holds on this lock by the current thread,
      *         or zero if this lock is not held by the current thread
@@ -545,7 +543,7 @@
      * testing. For example, a method that should only be called while
      * a lock is held can assert that this is the case:
      *
-     * <pre>
+     *  <pre> {@code
      * class X {
      *   ReentrantLock lock = new ReentrantLock();
      *   // ...
@@ -554,13 +552,12 @@
      *       assert lock.isHeldByCurrentThread();
      *       // ... method body
      *   }
-     * }
-     * </pre>
+     * }}</pre>
      *
      * <p>It can also be used to ensure that a reentrant lock is used
      * in a non-reentrant manner, for example:
      *
-     * <pre>
+     *  <pre> {@code
      * class X {
      *   ReentrantLock lock = new ReentrantLock();
      *   // ...
@@ -574,8 +571,7 @@
      *           lock.unlock();
      *       }
      *   }
-     * }
-     * </pre>
+     * }}</pre>
      *
      * @return {@code true} if current thread holds this lock and
      *         {@code false} otherwise
@@ -636,7 +632,6 @@
         return sync.hasQueuedThreads();
     }
 
-
     /**
      * Queries whether the given thread is waiting to acquire this
      * lock. Note that because cancellations may occur at any time, a
@@ -652,7 +647,6 @@
         return sync.isQueued(thread);
     }
 
-
     /**
      * Returns an estimate of the number of threads waiting to
      * acquire this lock.  The value is only an estimate because the number of
--- a/src/share/classes/java/util/concurrent/locks/ReentrantReadWriteLock.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/locks/ReentrantReadWriteLock.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,9 +34,8 @@
  */
 
 package java.util.concurrent.locks;
-import java.util.concurrent.*;
-import java.util.concurrent.atomic.*;
-import java.util.*;
+import java.util.concurrent.TimeUnit;
+import java.util.Collection;
 
 /**
  * An implementation of {@link ReadWriteLock} supporting similar
@@ -62,7 +61,7 @@
  * <dt><b><i>Fair mode</i></b>
  * <dd> When constructed as fair, threads contend for entry using an
  * approximately arrival-order policy. When the currently held lock
- * is released either the longest-waiting single writer thread will
+ * is released, either the longest-waiting single writer thread will
  * be assigned the write lock, or if there is a group of reader threads
  * waiting longer than all waiting writer threads, that group will be
  * assigned the read lock.
@@ -80,8 +79,8 @@
  * will block unless both the read lock and write lock are free (which
  * implies there are no waiting threads).  (Note that the non-blocking
  * {@link ReadLock#tryLock()} and {@link WriteLock#tryLock()} methods
- * do not honor this fair setting and will acquire the lock if it is
- * possible, regardless of waiting threads.)
+ * do not honor this fair setting and will immediately acquire the lock
+ * if it is possible, regardless of waiting threads.)
  * <p>
  * </dl>
  *
@@ -143,21 +142,21 @@
  *   void processCachedData() {
  *     rwl.readLock().lock();
  *     if (!cacheValid) {
- *        // Must release read lock before acquiring write lock
- *        rwl.readLock().unlock();
- *        rwl.writeLock().lock();
- *        try {
- *          // Recheck state because another thread might have
- *          // acquired write lock and changed state before we did.
- *          if (!cacheValid) {
- *            data = ...
- *            cacheValid = true;
- *          }
- *          // Downgrade by acquiring read lock before releasing write lock
- *          rwl.readLock().lock();
- *        } finally {
- *          rwl.writeLock().unlock(); // Unlock write, still hold read
- *        }
+ *       // Must release read lock before acquiring write lock
+ *       rwl.readLock().unlock();
+ *       rwl.writeLock().lock();
+ *       try {
+ *         // Recheck state because another thread might have
+ *         // acquired write lock and changed state before we did.
+ *         if (!cacheValid) {
+ *           data = ...
+ *           cacheValid = true;
+ *         }
+ *         // Downgrade by acquiring read lock before releasing write lock
+ *         rwl.readLock().lock();
+ *       } finally {
+ *         rwl.writeLock().unlock(); // Unlock write, still hold read
+ *       }
  *     }
  *
  *     try {
@@ -176,33 +175,33 @@
  * is a class using a TreeMap that is expected to be large and
  * concurrently accessed.
  *
- * <pre>{@code
+ *  <pre> {@code
  * class RWDictionary {
- *    private final Map<String, Data> m = new TreeMap<String, Data>();
- *    private final ReentrantReadWriteLock rwl = new ReentrantReadWriteLock();
- *    private final Lock r = rwl.readLock();
- *    private final Lock w = rwl.writeLock();
+ *   private final Map<String, Data> m = new TreeMap<String, Data>();
+ *   private final ReentrantReadWriteLock rwl = new ReentrantReadWriteLock();
+ *   private final Lock r = rwl.readLock();
+ *   private final Lock w = rwl.writeLock();
  *
- *    public Data get(String key) {
- *        r.lock();
- *        try { return m.get(key); }
- *        finally { r.unlock(); }
- *    }
- *    public String[] allKeys() {
- *        r.lock();
- *        try { return m.keySet().toArray(); }
- *        finally { r.unlock(); }
- *    }
- *    public Data put(String key, Data value) {
- *        w.lock();
- *        try { return m.put(key, value); }
- *        finally { w.unlock(); }
- *    }
- *    public void clear() {
- *        w.lock();
- *        try { m.clear(); }
- *        finally { w.unlock(); }
- *    }
+ *   public Data get(String key) {
+ *     r.lock();
+ *     try { return m.get(key); }
+ *     finally { r.unlock(); }
+ *   }
+ *   public String[] allKeys() {
+ *     r.lock();
+ *     try { return m.keySet().toArray(); }
+ *     finally { r.unlock(); }
+ *   }
+ *   public Data put(String key, Data value) {
+ *     w.lock();
+ *     try { return m.put(key, value); }
+ *     finally { w.unlock(); }
+ *   }
+ *   public void clear() {
+ *     w.lock();
+ *     try { m.clear(); }
+ *     finally { w.unlock(); }
+ *   }
  * }}</pre>
  *
  * <h3>Implementation Notes</h3>
@@ -213,7 +212,6 @@
  *
  * @since 1.5
  * @author Doug Lea
- *
  */
 public class ReentrantReadWriteLock
         implements ReadWriteLock, java.io.Serializable {
@@ -654,8 +652,7 @@
         }
 
         /**
-         * Reconstitute this lock instance from a stream
-         * @param s the stream
+         * Reconstitutes the instance from a stream (that is, deserializes it).
          */
         private void readObject(java.io.ObjectInputStream s)
             throws java.io.IOException, ClassNotFoundException {
@@ -799,7 +796,7 @@
          *
          * @return {@code true} if the read lock was acquired
          */
-        public  boolean tryLock() {
+        public boolean tryLock() {
             return sync.tryReadLock();
         }
 
@@ -819,8 +816,11 @@
          * permit barging on a fair lock then combine the timed and
          * un-timed forms together:
          *
-         * <pre>if (lock.tryLock() || lock.tryLock(timeout, unit) ) { ... }
-         * </pre>
+         *  <pre> {@code
+         * if (lock.tryLock() ||
+         *     lock.tryLock(timeout, unit)) {
+         *   ...
+         * }}</pre>
          *
          * <p>If the write lock is held by another thread then the
          * current thread becomes disabled for thread scheduling
@@ -866,7 +866,6 @@
          * @return {@code true} if the read lock was acquired
          * @throws InterruptedException if the current thread is interrupted
          * @throws NullPointerException if the time unit is null
-         *
          */
         public boolean tryLock(long timeout, TimeUnit unit)
                 throws InterruptedException {
@@ -879,7 +878,7 @@
          * <p> If the number of readers is now zero then the lock
          * is made available for write lock attempts.
          */
-        public  void unlock() {
+        public void unlock() {
             sync.releaseShared(1);
         }
 
@@ -1049,8 +1048,11 @@
          * that does permit barging on a fair lock then combine the
          * timed and un-timed forms together:
          *
-         * <pre>if (lock.tryLock() || lock.tryLock(timeout, unit) ) { ... }
-         * </pre>
+         *  <pre> {@code
+         * if (lock.tryLock() ||
+         *     lock.tryLock(timeout, unit)) {
+         *   ...
+         * }}</pre>
          *
          * <p>If the current thread already holds this lock then the
          * hold count is incremented by one and the method returns
@@ -1108,7 +1110,6 @@
          *
          * @throws InterruptedException if the current thread is interrupted
          * @throws NullPointerException if the time unit is null
-         *
          */
         public boolean tryLock(long timeout, TimeUnit unit)
                 throws InterruptedException {
--- a/src/share/classes/java/util/concurrent/package-info.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/concurrent/package-info.java	Mon Nov 05 10:33:18 2012 -0500
@@ -188,7 +188,7 @@
  * A {@code CopyOnWriteArrayList} is preferable to a synchronized
  * {@code ArrayList} when the expected number of reads and traversals
  * greatly outnumber the number of updates to a list.
-
+ *
  * <p>The "Concurrent" prefix used with some classes in this package
  * is a shorthand indicating several differences from similar
  * "synchronized" classes.  For example {@code java.util.Hashtable} and
@@ -218,9 +218,8 @@
  *
  * <h2><a name="MemoryVisibility">Memory Consistency Properties</a></h2>
  *
- * Chapter 17 of
- * <cite>The Java&trade; Language Specification</cite>
- * defines the
+ * <a href="http://docs.oracle.com/javase/specs/jls/se7/html/index.html">
+ * Chapter 17 of the Java Language Specification</a> defines the
  * <i>happens-before</i> relation on memory operations such as reads and
  * writes of shared variables.  The results of a write by one thread are
  * guaranteed to be visible to a read by another thread only if the write
--- a/src/share/classes/java/util/logging/ConsoleHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/ConsoleHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2003, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2012, 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
@@ -35,26 +35,39 @@
  * <p>
  * <b>Configuration:</b>
  * By default each <tt>ConsoleHandler</tt> is initialized using the following
- * <tt>LogManager</tt> configuration properties.  If properties are not defined
+ * <tt>LogManager</tt> configuration properties where <tt><handler-name></tt>
+ * refers to the fully-qualified class name of the handler.
+ * If properties are not defined
  * (or have invalid values) then the specified default values are used.
  * <ul>
- * <li>   java.util.logging.ConsoleHandler.level
+ * <li>   &lt;handler-name&gt;.level
  *        specifies the default level for the <tt>Handler</tt>
- *        (defaults to <tt>Level.INFO</tt>).
- * <li>   java.util.logging.ConsoleHandler.filter
+ *        (defaults to <tt>Level.INFO</tt>). </li>
+ * <li>   &lt;handler-name&gt;.filter
  *        specifies the name of a <tt>Filter</tt> class to use
- *        (defaults to no <tt>Filter</tt>).
- * <li>   java.util.logging.ConsoleHandler.formatter
+ *        (defaults to no <tt>Filter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.formatter
  *        specifies the name of a <tt>Formatter</tt> class to use
- *        (defaults to <tt>java.util.logging.SimpleFormatter</tt>).
- * <li>   java.util.logging.ConsoleHandler.encoding
+ *        (defaults to <tt>java.util.logging.SimpleFormatter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.encoding
  *        the name of the character set encoding to use (defaults to
- *        the default platform encoding).
+ *        the default platform encoding). </li>
+ * </ul>
+ * <p>
+ * For example, the properties for {@code ConsoleHandler} would be:
+ * <ul>
+ * <li>   java.util.logging.ConsoleHandler.level=INFO </li>
+ * <li>   java.util.logging.ConsoleHandler.formatter=java.util.logging.SimpleFormatter </li>
+ * </ul>
+ * <p>
+ * For a custom handler, e.g. com.foo.MyHandler, the properties would be:
+ * <ul>
+ * <li>   com.foo.MyHandler.level=INFO </li>
+ * <li>   com.foo.MyHandler.formatter=java.util.logging.SimpleFormatter </li>
  * </ul>
  * <p>
  * @since 1.4
  */
-
 public class ConsoleHandler extends StreamHandler {
     // Private method to configure a ConsoleHandler from LogManager
     // properties and/or default values as specified in the class
--- a/src/share/classes/java/util/logging/FileHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/FileHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2012, 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
@@ -48,45 +48,58 @@
  * <p>
  * <b>Configuration:</b>
  * By default each <tt>FileHandler</tt> is initialized using the following
- * <tt>LogManager</tt> configuration properties.  If properties are not defined
+ * <tt>LogManager</tt> configuration properties where <tt>&lt;handler-name&gt;</tt>
+ * refers to the fully-qualified class name of the handler.
+ * If properties are not defined
  * (or have invalid values) then the specified default values are used.
  * <ul>
- * <li>   java.util.logging.FileHandler.level
+ * <li>   &lt;handler-name&gt;.level
  *        specifies the default level for the <tt>Handler</tt>
- *        (defaults to <tt>Level.ALL</tt>).
- * <li>   java.util.logging.FileHandler.filter
+ *        (defaults to <tt>Level.ALL</tt>). </li>
+ * <li>   &lt;handler-name&gt;.filter
  *        specifies the name of a <tt>Filter</tt> class to use
- *        (defaults to no <tt>Filter</tt>).
- * <li>   java.util.logging.FileHandler.formatter
+ *        (defaults to no <tt>Filter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.formatter
  *        specifies the name of a <tt>Formatter</tt> class to use
- *        (defaults to <tt>java.util.logging.XMLFormatter</tt>)
- * <li>   java.util.logging.FileHandler.encoding
+ *        (defaults to <tt>java.util.logging.XMLFormatter</tt>) </li>
+ * <li>   &lt;handler-name&gt;.encoding
  *        the name of the character set encoding to use (defaults to
- *        the default platform encoding).
- * <li>   java.util.logging.FileHandler.limit
+ *        the default platform encoding). </li>
+ * <li>   &lt;handler-name&gt;.limit
  *        specifies an approximate maximum amount to write (in bytes)
  *        to any one file.  If this is zero, then there is no limit.
- *        (Defaults to no limit).
- * <li>   java.util.logging.FileHandler.count
- *        specifies how many output files to cycle through (defaults to 1).
- * <li>   java.util.logging.FileHandler.pattern
+ *        (Defaults to no limit). </li>
+ * <li>   &lt;handler-name&gt;.count
+ *        specifies how many output files to cycle through (defaults to 1). </li>
+ * <li>   &lt;handler-name&gt;.pattern
  *        specifies a pattern for generating the output file name.  See
- *        below for details. (Defaults to "%h/java%u.log").
- * <li>   java.util.logging.FileHandler.append
+ *        below for details. (Defaults to "%h/java%u.log"). </li>
+ * <li>   &lt;handler-name&gt;.append
  *        specifies whether the FileHandler should append onto
- *        any existing files (defaults to false).
+ *        any existing files (defaults to false). </li>
  * </ul>
  * <p>
+ * For example, the properties for {@code FileHandler} would be:
+ * <ul>
+ * <li>   java.util.logging.FileHandler.level=INFO </li>
+ * <li>   java.util.logging.FileHandler.formatter=java.util.logging.SimpleFormatter </li>
+ * </ul>
+ * <p>
+ * For a custom handler, e.g. com.foo.MyHandler, the properties would be:
+ * <ul>
+ * <li>   com.foo.MyHandler.level=INFO </li>
+ * <li>   com.foo.MyHandler.formatter=java.util.logging.SimpleFormatter </li>
+ * </ul>
  * <p>
  * A pattern consists of a string that includes the following special
  * components that will be replaced at runtime:
  * <ul>
- * <li>    "/"    the local pathname separator
- * <li>     "%t"   the system temporary directory
- * <li>     "%h"   the value of the "user.home" system property
- * <li>     "%g"   the generation number to distinguish rotated logs
- * <li>     "%u"   a unique number to resolve conflicts
- * <li>     "%%"   translates to a single percent sign "%"
+ * <li>    "/"    the local pathname separator </li>
+ * <li>     "%t"   the system temporary directory </li>
+ * <li>     "%h"   the value of the "user.home" system property </li>
+ * <li>     "%g"   the generation number to distinguish rotated logs </li>
+ * <li>     "%u"   a unique number to resolve conflicts </li>
+ * <li>     "%%"   translates to a single percent sign "%" </li>
  * </ul>
  * If no "%g" field has been specified and the file count is greater
  * than one, then the generation number will be added to the end of
@@ -220,7 +233,7 @@
      * @exception  NullPointerException if pattern property is an empty String.
      */
     public FileHandler() throws IOException, SecurityException {
-        checkAccess();
+        checkPermission();
         configure();
         openFiles();
     }
@@ -246,7 +259,7 @@
         if (pattern.length() < 1 ) {
             throw new IllegalArgumentException();
         }
-        checkAccess();
+        checkPermission();
         configure();
         this.pattern = pattern;
         this.limit = 0;
@@ -278,7 +291,7 @@
         if (pattern.length() < 1 ) {
             throw new IllegalArgumentException();
         }
-        checkAccess();
+        checkPermission();
         configure();
         this.pattern = pattern;
         this.limit = 0;
@@ -315,7 +328,7 @@
         if (limit < 0 || count < 1 || pattern.length() < 1) {
             throw new IllegalArgumentException();
         }
-        checkAccess();
+        checkPermission();
         configure();
         this.pattern = pattern;
         this.limit = limit;
@@ -354,7 +367,7 @@
         if (limit < 0 || count < 1 || pattern.length() < 1) {
             throw new IllegalArgumentException();
         }
-        checkAccess();
+        checkPermission();
         configure();
         this.pattern = pattern;
         this.limit = limit;
@@ -367,7 +380,7 @@
     // configured instance variables.
     private void openFiles() throws IOException {
         LogManager manager = LogManager.getLogManager();
-        manager.checkAccess();
+        manager.checkPermission();
         if (count < 1) {
            throw new IllegalArgumentException("file count = " + count);
         }
--- a/src/share/classes/java/util/logging/Handler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/Handler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -111,7 +111,7 @@
      *             the caller does not have <tt>LoggingPermission("control")</tt>.
      */
     public void setFormatter(Formatter newFormatter) throws SecurityException {
-        checkAccess();
+        checkPermission();
         // Check for a null pointer:
         newFormatter.getClass();
         formatter = newFormatter;
@@ -140,7 +140,7 @@
      */
     public void setEncoding(String encoding)
                         throws SecurityException, java.io.UnsupportedEncodingException {
-        checkAccess();
+        checkPermission();
         if (encoding != null) {
             try {
                 if(!java.nio.charset.Charset.isSupported(encoding)) {
@@ -175,7 +175,7 @@
      *             the caller does not have <tt>LoggingPermission("control")</tt>.
      */
     public void setFilter(Filter newFilter) throws SecurityException {
-        checkAccess();
+        checkPermission();
         filter = newFilter;
     }
 
@@ -199,7 +199,7 @@
      *             the caller does not have <tt>LoggingPermission("control")</tt>.
      */
     public void setErrorManager(ErrorManager em) {
-        checkAccess();
+        checkPermission();
         if (em == null) {
            throw new NullPointerException();
         }
@@ -213,7 +213,7 @@
      *             the caller does not have <tt>LoggingPermission("control")</tt>.
      */
     public ErrorManager getErrorManager() {
-        checkAccess();
+        checkPermission();
         return errorManager;
     }
 
@@ -253,7 +253,7 @@
         if (newLevel == null) {
             throw new NullPointerException();
         }
-        checkAccess();
+        checkPermission();
         logLevel = newLevel;
     }
 
@@ -296,9 +296,9 @@
     // If "sealed" is true, we check that the caller has
     // appropriate security privileges to update Handler
     // state and if not throw a SecurityException.
-    void checkAccess() throws SecurityException {
+    void checkPermission() throws SecurityException {
         if (sealed) {
-            manager.checkAccess();
+            manager.checkPermission();
         }
     }
 }
--- a/src/share/classes/java/util/logging/LogManager.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/LogManager.java	Mon Nov 05 10:33:18 2012 -0500
@@ -321,7 +321,7 @@
     @Deprecated
     public void addPropertyChangeListener(PropertyChangeListener l) throws SecurityException {
         PropertyChangeListener listener = Objects.requireNonNull(l);
-        checkAccess();
+        checkPermission();
         synchronized (listenerMap) {
             // increment the registration count if already registered
             Integer value = listenerMap.get(listener);
@@ -352,7 +352,7 @@
      */
     @Deprecated
     public void removePropertyChangeListener(PropertyChangeListener l) throws SecurityException {
-        checkAccess();
+        checkPermission();
         if (l != null) {
             PropertyChangeListener listener = l;
             synchronized (listenerMap) {
@@ -807,7 +807,7 @@
      * @exception  IOException if there are IO problems reading the configuration.
      */
     public void readConfiguration() throws IOException, SecurityException {
-        checkAccess();
+        checkPermission();
 
         // if a configuration class is specified, load it and use it.
         String cname = System.getProperty("java.util.logging.config.class");
@@ -865,7 +865,7 @@
      */
 
     public void reset() throws SecurityException {
-        checkAccess();
+        checkPermission();
         synchronized (this) {
             props = new Properties();
             // Since we are doing a reset we no longer want to initialize
@@ -950,7 +950,7 @@
      * @exception  IOException if there are problems reading from the stream.
      */
     public void readConfiguration(InputStream ins) throws IOException, SecurityException {
-        checkAccess();
+        checkPermission();
         reset();
 
         // Load the properties
@@ -1127,8 +1127,13 @@
         loadLoggerHandlers(rootLogger, null, "handlers");
     }
 
+    private final Permission controlPermission = new LoggingPermission("control", null);
 
-    private Permission ourPermission = new LoggingPermission("control", null);
+    void checkPermission() {
+        SecurityManager sm = System.getSecurityManager();
+        if (sm != null)
+            sm.checkPermission(controlPermission);
+    }
 
     /**
      * Check that the current context is trusted to modify the logging
@@ -1141,11 +1146,7 @@
      *             the caller does not have LoggingPermission("control").
      */
     public void checkAccess() throws SecurityException {
-        SecurityManager sm = System.getSecurityManager();
-        if (sm == null) {
-            return;
-        }
-        sm.checkPermission(ourPermission);
+        checkPermission();
     }
 
     // Nested class to represent a node in our tree of named loggers.
--- a/src/share/classes/java/util/logging/Logger.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/Logger.java	Mon Nov 05 10:33:18 2012 -0500
@@ -276,13 +276,13 @@
         this.manager = manager;
     }
 
-    private void checkAccess() throws SecurityException {
+    private void checkPermission() throws SecurityException {
         if (!anonymous) {
             if (manager == null) {
                 // Complete initialization of the global Logger.
                 manager = LogManager.getLogManager();
             }
-            manager.checkAccess();
+            manager.checkPermission();
         }
     }
 
@@ -482,7 +482,7 @@
      *             the caller does not have LoggingPermission("control").
      */
     public void setFilter(Filter newFilter) throws SecurityException {
-        checkAccess();
+        checkPermission();
         filter = newFilter;
     }
 
@@ -1168,7 +1168,7 @@
      *             the caller does not have LoggingPermission("control").
      */
     public void setLevel(Level newLevel) throws SecurityException {
-        checkAccess();
+        checkPermission();
         synchronized (treeLock) {
             levelObject = newLevel;
             updateEffectiveLevel();
@@ -1223,7 +1223,7 @@
     public void addHandler(Handler handler) throws SecurityException {
         // Check for null handler
         handler.getClass();
-        checkAccess();
+        checkPermission();
         handlers.add(handler);
     }
 
@@ -1237,7 +1237,7 @@
      *             the caller does not have LoggingPermission("control").
      */
     public void removeHandler(Handler handler) throws SecurityException {
-        checkAccess();
+        checkPermission();
         if (handler == null) {
             return;
         }
@@ -1265,7 +1265,7 @@
      *             the caller does not have LoggingPermission("control").
      */
     public void setUseParentHandlers(boolean useParentHandlers) {
-        checkAccess();
+        checkPermission();
         this.useParentHandlers = useParentHandlers;
     }
 
@@ -1420,7 +1420,7 @@
         if (parent == null) {
             throw new NullPointerException();
         }
-        manager.checkAccess();
+        manager.checkPermission();
         doSetParent(parent);
     }
 
--- a/src/share/classes/java/util/logging/MemoryHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/MemoryHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2004, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2012, 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
@@ -39,36 +39,50 @@
  * <ul>
  * <li>
  * An incoming <tt>LogRecord</tt> has a type that is greater than
- * a pre-defined level, the <tt>pushLevel</tt>.
+ * a pre-defined level, the <tt>pushLevel</tt>. </li>
  * <li>
- * An external class calls the <tt>push</tt> method explicitly.
+ * An external class calls the <tt>push</tt> method explicitly. </li>
  * <li>
  * A subclass overrides the <tt>log</tt> method and scans each incoming
  * <tt>LogRecord</tt> and calls <tt>push</tt> if a record matches some
- * desired criteria.
+ * desired criteria. </li>
  * </ul>
  * <p>
  * <b>Configuration:</b>
  * By default each <tt>MemoryHandler</tt> is initialized using the following
- * LogManager configuration properties.  If properties are not defined
+ * <tt>LogManager</tt> configuration properties where <tt>&lt;handler-name&gt;</tt>
+ * refers to the fully-qualified class name of the handler.
+ * If properties are not defined
  * (or have invalid values) then the specified default values are used.
  * If no default value is defined then a RuntimeException is thrown.
  * <ul>
- * <li>   java.util.logging.MemoryHandler.level
+ * <li>   &lt;handler-name&gt;.level
  *        specifies the level for the <tt>Handler</tt>
- *        (defaults to <tt>Level.ALL</tt>).
- * <li>   java.util.logging.MemoryHandler.filter
+ *        (defaults to <tt>Level.ALL</tt>). </li>
+ * <li>   &lt;handler-name&gt;.filter
  *        specifies the name of a <tt>Filter</tt> class to use
- *        (defaults to no <tt>Filter</tt>).
- * <li>   java.util.logging.MemoryHandler.size
- *        defines the buffer size (defaults to 1000).
- * <li>   java.util.logging.MemoryHandler.push
- *        defines the <tt>pushLevel</tt> (defaults to <tt>level.SEVERE</tt>).
- * <li>   java.util.logging.MemoryHandler.target
+ *        (defaults to no <tt>Filter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.size
+ *        defines the buffer size (defaults to 1000). </li>
+ * <li>   &lt;handler-name>.push
+ *        defines the <tt>pushLevel</tt> (defaults to <tt>level.SEVERE</tt>). </li>
+ * <li>   &lt;handler-name&gt;.target
  *        specifies the name of the target <tt>Handler </tt> class.
- *        (no default).
+ *        (no default). </li>
+ * </ul>
+ * <p>
+ * For example, the properties for {@code MemoryHandler} would be:
+ * <ul>
+ * <li>   java.util.logging.MemoryHandler.level=INFO </li>
+ * <li>   java.util.logging.MemoryHandler.formatter=java.util.logging.SimpleFormatter </li>
  * </ul>
- *
+ * <p>
+ * For a custom handler, e.g. com.foo.MyHandler, the properties would be:
+ * <ul>
+ * <li>   com.foo.MyHandler.level=INFO </li>
+ * <li>   com.foo.MyHandler.formatter=java.util.logging.SimpleFormatter </li>
+ * </ul>
+ * <p>
  * @since 1.4
  */
 
@@ -80,7 +94,7 @@
     private LogRecord buffer[];
     int start, count;
 
-    // Private method to configure a ConsoleHandler from LogManager
+    // Private method to configure a MemoryHandler from LogManager
     // properties and/or default values as specified in the class
     // javadoc.
     private void configure() {
@@ -106,14 +120,19 @@
         configure();
         sealed = true;
 
-        String name = "???";
+        LogManager manager = LogManager.getLogManager();
+        String handlerName = getClass().getName();
+        String targetName = manager.getProperty(handlerName+".target");
+        if (targetName == null) {
+            throw new RuntimeException("The handler " + handlerName
+                    + " does not specify a target");
+        }
+        Class<?> clz;
         try {
-            LogManager manager = LogManager.getLogManager();
-            name = manager.getProperty("java.util.logging.MemoryHandler.target");
-            Class clz = ClassLoader.getSystemClassLoader().loadClass(name);
+            clz = ClassLoader.getSystemClassLoader().loadClass(targetName);
             target = (Handler) clz.newInstance();
-        } catch (Exception ex) {
-            throw new RuntimeException("MemoryHandler can't load handler \"" + name + "\"" , ex);
+        } catch (ClassNotFoundException | InstantiationException | IllegalAccessException e) {
+            throw new RuntimeException("MemoryHandler can't load handler target \"" + targetName + "\"" , e);
         }
         init();
     }
@@ -238,7 +257,7 @@
             throw new NullPointerException();
         }
         LogManager manager = LogManager.getLogManager();
-        checkAccess();
+        checkPermission();
         pushLevel = newLevel;
     }
 
--- a/src/share/classes/java/util/logging/SocketHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/SocketHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2003, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2012, 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
@@ -37,25 +37,39 @@
  * <p>
  * <b>Configuration:</b>
  * By default each <tt>SocketHandler</tt> is initialized using the following
- * <tt>LogManager</tt> configuration properties.  If properties are not defined
+ * <tt>LogManager</tt> configuration properties where <tt>&lt;handler-name&gt;</tt>
+ * refers to the fully-qualified class name of the handler.
+ * If properties are not defined
  * (or have invalid values) then the specified default values are used.
  * <ul>
- * <li>   java.util.logging.SocketHandler.level
+ * <li>   &lt;handler-name&gt;.level
  *        specifies the default level for the <tt>Handler</tt>
- *        (defaults to <tt>Level.ALL</tt>).
- * <li>   java.util.logging.SocketHandler.filter
+ *        (defaults to <tt>Level.ALL</tt>). </li>
+ * <li>   &lt;handler-name&gt;.filter
  *        specifies the name of a <tt>Filter</tt> class to use
- *        (defaults to no <tt>Filter</tt>).
- * <li>   java.util.logging.SocketHandler.formatter
+ *        (defaults to no <tt>Filter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.formatter
  *        specifies the name of a <tt>Formatter</tt> class to use
- *        (defaults to <tt>java.util.logging.XMLFormatter</tt>).
- * <li>   java.util.logging.SocketHandler.encoding
+ *        (defaults to <tt>java.util.logging.XMLFormatter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.encoding
  *        the name of the character set encoding to use (defaults to
- *        the default platform encoding).
- * <li>   java.util.logging.SocketHandler.host
- *        specifies the target host name to connect to (no default).
- * <li>   java.util.logging.SocketHandler.port
- *        specifies the target TCP port to use (no default).
+ *        the default platform encoding). </li>
+ * <li>   &lt;handler-name&gt;.host
+ *        specifies the target host name to connect to (no default). </li>
+ * <li>   &lt;handler-name&gt;.port
+ *        specifies the target TCP port to use (no default). </li>
+ * </ul>
+ * <p>
+ * For example, the properties for {@code SocketHandler} would be:
+ * <ul>
+ * <li>   java.util.logging.SocketHandler.level=INFO </li>
+ * <li>   java.util.logging.SocketHandler.formatter=java.util.logging.SimpleFormatter </li>
+ * </ul>
+ * <p>
+ * For a custom handler, e.g. com.foo.MyHandler, the properties would be:
+ * <ul>
+ * <li>   com.foo.MyHandler.level=INFO </li>
+ * <li>   com.foo.MyHandler.formatter=java.util.logging.SimpleFormatter </li>
  * </ul>
  * <p>
  * The output IO stream is buffered, but is flushed after each
--- a/src/share/classes/java/util/logging/StreamHandler.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/java/util/logging/StreamHandler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2000, 2006, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2000, 2012, 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
@@ -38,23 +38,37 @@
  * <p>
  * <b>Configuration:</b>
  * By default each <tt>StreamHandler</tt> is initialized using the following
- * <tt>LogManager</tt> configuration properties.  If properties are not defined
+ * <tt>LogManager</tt> configuration properties where <tt>&lt;handler-name&gt;</tt>
+ * refers to the fully-qualified class name of the handler.
+ * If properties are not defined
  * (or have invalid values) then the specified default values are used.
  * <ul>
- * <li>   java.util.logging.StreamHandler.level
+ * <li>   &lt;handler-name&gt;.level
  *        specifies the default level for the <tt>Handler</tt>
- *        (defaults to <tt>Level.INFO</tt>).
- * <li>   java.util.logging.StreamHandler.filter
+ *        (defaults to <tt>Level.INFO</tt>). </li>
+ * <li>   &lt;handler-name&gt;.filter
  *        specifies the name of a <tt>Filter</tt> class to use
- *         (defaults to no <tt>Filter</tt>).
- * <li>   java.util.logging.StreamHandler.formatter
+ *         (defaults to no <tt>Filter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.formatter
  *        specifies the name of a <tt>Formatter</tt> class to use
- *        (defaults to <tt>java.util.logging.SimpleFormatter</tt>).
- * <li>   java.util.logging.StreamHandler.encoding
+ *        (defaults to <tt>java.util.logging.SimpleFormatter</tt>). </li>
+ * <li>   &lt;handler-name&gt;.encoding
  *        the name of the character set encoding to use (defaults to
- *        the default platform encoding).
+ *        the default platform encoding). </li>
+ * </ul>
+ * <p>
+ * For example, the properties for {@code StreamHandler} would be:
+ * <ul>
+ * <li>   java.util.logging.StreamHandler.level=INFO </li>
+ * <li>   java.util.logging.StreamHandler.formatter=java.util.logging.SimpleFormatter </li>
  * </ul>
- *
+ * <p>
+ * For a custom handler, e.g. com.foo.MyHandler, the properties would be:
+ * <ul>
+ * <li>   com.foo.MyHandler.level=INFO </li>
+ * <li>   com.foo.MyHandler.formatter=java.util.logging.SimpleFormatter </li>
+ * </ul>
+ * <p>
  * @since 1.4
  */
 
@@ -249,7 +263,7 @@
     }
 
     private synchronized void flushAndClose() throws SecurityException {
-        checkAccess();
+        checkPermission();
         if (writer != null) {
             try {
                 if (!doneHeader) {
--- a/src/share/classes/javax/management/modelmbean/DescriptorSupport.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/management/modelmbean/DescriptorSupport.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1245,13 +1245,12 @@
             return s.substring(1, s.length() - 1);
         }
         final String className = s.substring(1, slash);
+
         final Constructor<?> constr;
         try {
+            ReflectUtil.checkPackageAccess(className);
             final ClassLoader contextClassLoader =
                 Thread.currentThread().getContextClassLoader();
-            if (contextClassLoader == null) {
-                ReflectUtil.checkPackageAccess(className);
-            }
             final Class<?> c =
                 Class.forName(className, false, contextClassLoader);
             constr = c.getConstructor(new Class<?>[] {String.class});
--- a/src/share/classes/javax/management/remote/rmi/RMIConnectionImpl.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/management/remote/rmi/RMIConnectionImpl.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2002, 2008, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2002, 2012, 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
@@ -25,6 +25,30 @@
 
 package javax.management.remote.rmi;
 
+import java.io.IOException;
+import java.rmi.MarshalledObject;
+import java.rmi.UnmarshalException;
+import java.rmi.server.Unreferenced;
+import java.security.AccessControlContext;
+import java.security.AccessController;
+import java.security.Permission;
+import java.security.PermissionCollection;
+import java.security.Permissions;
+import java.security.PrivilegedAction;
+import java.security.PrivilegedActionException;
+import java.security.PrivilegedExceptionAction;
+import java.security.ProtectionDomain;
+import java.util.Arrays;
+import java.util.Collections;
+import java.util.Map;
+import java.util.Set;
+
+import javax.management.*;
+import javax.management.remote.JMXServerErrorException;
+import javax.management.remote.NotificationResult;
+import javax.management.remote.TargetedNotification;
+import javax.security.auth.Subject;
+
 import static com.sun.jmx.mbeanserver.Util.cast;
 import com.sun.jmx.remote.internal.ServerCommunicatorAdmin;
 import com.sun.jmx.remote.internal.ServerNotifForwarder;
@@ -35,44 +59,6 @@
 import com.sun.jmx.remote.util.EnvHelp;
 import com.sun.jmx.remote.util.OrderClassLoaders;
 
-import java.io.IOException;
-import java.rmi.MarshalledObject;
-import java.rmi.UnmarshalException;
-import java.rmi.server.Unreferenced;
-import java.security.AccessControlContext;
-import java.security.AccessController;
-import java.security.PrivilegedAction;
-import java.security.PrivilegedActionException;
-import java.security.PrivilegedExceptionAction;
-import java.util.Arrays;
-import java.util.Collections;
-import java.util.Map;
-import java.util.Set;
-
-import javax.management.Attribute;
-import javax.management.AttributeList;
-import javax.management.AttributeNotFoundException;
-import javax.management.InstanceAlreadyExistsException;
-import javax.management.InstanceNotFoundException;
-import javax.management.IntrospectionException;
-import javax.management.InvalidAttributeValueException;
-import javax.management.ListenerNotFoundException;
-import javax.management.MBeanException;
-import javax.management.MBeanInfo;
-import javax.management.MBeanRegistrationException;
-import javax.management.MBeanServer;
-import javax.management.NotCompliantMBeanException;
-import javax.management.NotificationFilter;
-import javax.management.ObjectInstance;
-import javax.management.ObjectName;
-import javax.management.QueryExp;
-import javax.management.ReflectionException;
-import javax.management.RuntimeOperationsException;
-import javax.management.remote.JMXServerErrorException;
-import javax.management.remote.NotificationResult;
-import javax.management.remote.TargetedNotification;
-import javax.security.auth.Subject;
-
 /**
  * <p>Implementation of the {@link RMIConnection} interface.  User
  * code will not usually reference this class.</p>
@@ -143,6 +129,7 @@
         this.mbeanServer = rmiServer.getMBeanServer();
 
         final ClassLoader dcl = defaultClassLoader;
+
         this.classLoaderWithRepository =
             AccessController.doPrivileged(
                 new PrivilegedAction<ClassLoaderWithRepository>() {
@@ -151,13 +138,40 @@
                                       mbeanServer.getClassLoaderRepository(),
                                       dcl);
                     }
+                },
+
+                withPermissions( new MBeanPermission("*", "getClassLoaderRepository"),
+                                 new RuntimePermission("createClassLoader"))
+            );
+
+
+        this.defaultContextClassLoader =
+            AccessController.doPrivileged(
+                new PrivilegedAction<ClassLoader>() {
+            @Override
+                    public ClassLoader run() {
+                        return new CombinedClassLoader(Thread.currentThread().getContextClassLoader(),
+                                dcl);
+                    }
                 });
+
         serverCommunicatorAdmin = new
           RMIServerCommunicatorAdmin(EnvHelp.getServerConnectionTimeout(env));
 
         this.env = env;
     }
 
+    private static AccessControlContext withPermissions(Permission ... perms){
+        Permissions col = new Permissions();
+
+        for (Permission thePerm : perms ) {
+            col.add(thePerm);
+        }
+
+        final ProtectionDomain pd = new ProtectionDomain(null, col);
+        return new AccessControlContext( new ProtectionDomain[] { pd });
+    }
+
     private synchronized ServerNotifForwarder getServerNotifFwd() {
         // Lazily created when first use. Mainly when
         // addNotificationListener is first called.
@@ -507,7 +521,7 @@
                  "connectionId=" + connectionId
                  +" unwrapping query with defaultClassLoader.");
 
-        queryValue = unwrap(query, defaultClassLoader, QueryExp.class);
+        queryValue = unwrap(query, defaultContextClassLoader, QueryExp.class);
 
         try {
             final Object params[] = new Object[] { name, queryValue };
@@ -542,7 +556,7 @@
                  "connectionId=" + connectionId
                  +" unwrapping query with defaultClassLoader.");
 
-        queryValue = unwrap(query, defaultClassLoader, QueryExp.class);
+        queryValue = unwrap(query, defaultContextClassLoader, QueryExp.class);
 
         try {
             final Object params[] = new Object[] { name, queryValue };
@@ -1330,7 +1344,9 @@
                         public ClassLoader run() throws InstanceNotFoundException {
                             return mbeanServer.getClassLoader(name);
                         }
-                    });
+                    },
+                    withPermissions(new MBeanPermission("*", "getClassLoader"))
+            );
         } catch (PrivilegedActionException pe) {
             throw (InstanceNotFoundException) extractException(pe);
         }
@@ -1345,7 +1361,9 @@
                         public Object run() throws InstanceNotFoundException {
                             return mbeanServer.getClassLoaderFor(name);
                         }
-                    });
+                    },
+                    withPermissions(new MBeanPermission("*", "getClassLoaderFor"))
+            );
         } catch (PrivilegedActionException pe) {
             throw (InstanceNotFoundException) extractException(pe);
         }
@@ -1572,7 +1590,8 @@
             ClassLoader orderCL = AccessController.doPrivileged(
                 new PrivilegedExceptionAction<ClassLoader>() {
                     public ClassLoader run() throws Exception {
-                        return new OrderClassLoaders(cl1, cl2);
+                        return new CombinedClassLoader(Thread.currentThread().getContextClassLoader(),
+                                new OrderClassLoaders(cl1, cl2));
                     }
                 }
             );
@@ -1664,6 +1683,8 @@
 
     private final ClassLoader defaultClassLoader;
 
+    private final ClassLoader defaultContextClassLoader;
+
     private final ClassLoaderWithRepository classLoaderWithRepository;
 
     private boolean terminated = false;
@@ -1746,4 +1767,43 @@
 
     private static final ClassLogger logger =
         new ClassLogger("javax.management.remote.rmi", "RMIConnectionImpl");
+
+    private static final class CombinedClassLoader extends ClassLoader {
+
+        private final static class ClassLoaderWrapper extends ClassLoader {
+            ClassLoaderWrapper(ClassLoader cl) {
+                super(cl);
+            }
+
+            @Override
+            protected Class<?> loadClass(String name, boolean resolve)
+                    throws ClassNotFoundException {
+                return super.loadClass(name, resolve);
+            }
+        };
+
+        final ClassLoaderWrapper defaultCL;
+
+        private CombinedClassLoader(ClassLoader parent, ClassLoader defaultCL) {
+            super(parent);
+            this.defaultCL = new ClassLoaderWrapper(defaultCL);
+        }
+
+        @Override
+        protected Class<?> loadClass(String name, boolean resolve)
+        throws ClassNotFoundException {
+            try {
+                super.loadClass(name, resolve);
+            } catch(Exception e) {
+                for(Throwable t = e; t != null; t = t.getCause()) {
+                    if(t instanceof SecurityException) {
+                        throw t==e?(SecurityException)t:new SecurityException(t.getMessage(), e);
+                    }
+                }
+            }
+            final Class<?> cl = defaultCL.loadClass(name, resolve);
+            return cl;
+        }
+
+    }
 }
--- a/src/share/classes/javax/management/remote/rmi/RMIConnector.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/management/remote/rmi/RMIConnector.java	Mon Nov 05 10:33:18 2012 -0500
@@ -277,9 +277,9 @@
             // Check for secure RMIServer stub if the corresponding
             // client-side environment property is set to "true".
             //
-            boolean checkStub = EnvHelp.computeBooleanFromString(
-                    usemap,
-                    "jmx.remote.x.check.stub",false);
+            String stringBoolean =  (String) usemap.get("jmx.remote.x.check.stub");
+            boolean checkStub = EnvHelp.computeBooleanFromString(stringBoolean);
+
             if (checkStub) checkStub(stub, rmiServerImplStubClass);
 
             // Connect IIOP Stub if needed.
--- a/src/share/classes/javax/management/remote/rmi/RMIConnectorServer.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/management/remote/rmi/RMIConnectorServer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -412,9 +412,8 @@
                 if (tracing)
                     logger.trace("start", "Using external directory: " + jndiUrl);
 
-                final boolean rebind = EnvHelp.computeBooleanFromString(
-                    attributes,
-                    JNDI_REBIND_ATTRIBUTE,false);
+                String stringBoolean = (String) attributes.get(JNDI_REBIND_ATTRIBUTE);
+                final boolean rebind = EnvHelp.computeBooleanFromString( stringBoolean );
 
                 if (tracing)
                     logger.trace("start", JNDI_REBIND_ATTRIBUTE + "=" + rebind);
--- a/src/share/classes/javax/management/timer/Timer.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/management/timer/Timer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1240,54 +1240,3 @@
                 "sendNotification", "timer notification sent");
     }
 }
-
-/**
- * TimerAlarmClock inner class:
- * This class provides a simple implementation of an alarm clock MBean.
- * The aim of this MBean is to set up an alarm which wakes up the timer every timeout (fixed-delay)
- * or at the specified date (fixed-rate).
- */
-
-class TimerAlarmClock extends java.util.TimerTask {
-
-    Timer listener = null;
-    long timeout = 10000;
-    Date next = null;
-
-    /*
-     * ------------------------------------------
-     *  CONSTRUCTORS
-     * ------------------------------------------
-     */
-
-    public TimerAlarmClock(Timer listener, long timeout) {
-        this.listener = listener;
-        this.timeout = Math.max(0L, timeout);
-    }
-
-    public TimerAlarmClock(Timer listener, Date next) {
-        this.listener = listener;
-        this.next = next;
-    }
-
-    /*
-     * ------------------------------------------
-     *  PUBLIC METHODS
-     * ------------------------------------------
-     */
-
-    /**
-     * This method is called by the timer when it is started.
-     */
-    public void run() {
-
-        try {
-            //this.sleep(timeout);
-            TimerAlarmClockNotification notif = new TimerAlarmClockNotification(this);
-            listener.notifyAlarmClock(notif);
-        } catch (Exception e) {
-            TIMER_LOGGER.logp(Level.FINEST, Timer.class.getName(), "run",
-                    "Got unexpected exception when sending a notification", e);
-        }
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/javax/management/timer/TimerAlarmClock.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,80 @@
+/*
+ * Copyright (c) 1999, 2008, 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 javax.management.timer;
+
+import java.util.Date;
+import java.util.logging.Level;
+import static com.sun.jmx.defaults.JmxProperties.TIMER_LOGGER;
+
+/**
+ * This class provides a simple implementation of an alarm clock MBean.
+ * The aim of this MBean is to set up an alarm which wakes up the timer every timeout (fixed-delay)
+ * or at the specified date (fixed-rate).
+ */
+
+class TimerAlarmClock extends java.util.TimerTask {
+
+    Timer listener = null;
+    long timeout = 10000;
+    Date next = null;
+
+    /*
+     * ------------------------------------------
+     *  CONSTRUCTORS
+     * ------------------------------------------
+     */
+
+    public TimerAlarmClock(Timer listener, long timeout) {
+        this.listener = listener;
+        this.timeout = Math.max(0L, timeout);
+    }
+
+    public TimerAlarmClock(Timer listener, Date next) {
+        this.listener = listener;
+        this.next = next;
+    }
+
+    /*
+     * ------------------------------------------
+     *  PUBLIC METHODS
+     * ------------------------------------------
+     */
+
+    /**
+     * This method is called by the timer when it is started.
+     */
+    public void run() {
+
+        try {
+            //this.sleep(timeout);
+            TimerAlarmClockNotification notif = new TimerAlarmClockNotification(this);
+            listener.notifyAlarmClock(notif);
+        } catch (Exception e) {
+            TIMER_LOGGER.logp(Level.FINEST, Timer.class.getName(), "run",
+                    "Got unexpected exception when sending a notification", e);
+        }
+    }
+}
--- a/src/share/classes/javax/net/ssl/SSLParameters.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/net/ssl/SSLParameters.java	Mon Nov 05 10:33:18 2012 -0500
@@ -291,7 +291,7 @@
      *
      * @since 1.8
      */
-    public void setServerNames(List<SNIServerName> serverNames) {
+    public final void setServerNames(List<SNIServerName> serverNames) {
         if (serverNames != null) {
             if (!serverNames.isEmpty()) {
                 sniNames = new LinkedHashMap<>(serverNames.size());
@@ -349,7 +349,7 @@
      *
      * @since 1.8
      */
-    public List<SNIServerName> getServerNames() {
+    public final List<SNIServerName> getServerNames() {
         if (sniNames != null) {
             if (!sniNames.isEmpty()) {
                 return Collections.<SNIServerName>unmodifiableList(
@@ -386,7 +386,7 @@
      *
      * @since 1.8
      */
-    public void setSNIMatchers(Collection<SNIMatcher> matchers) {
+    public final void setSNIMatchers(Collection<SNIMatcher> matchers) {
         if (matchers != null) {
             if (!matchers.isEmpty()) {
                 sniMatchers = new HashMap<>(matchers.size());
@@ -424,7 +424,7 @@
      *
      * @since 1.8
      */
-    public Collection<SNIMatcher> getSNIMatchers() {
+    public final Collection<SNIMatcher> getSNIMatchers() {
         if (sniMatchers != null) {
             if (!sniMatchers.isEmpty()) {
                 return Collections.<SNIMatcher>unmodifiableList(
--- a/src/share/classes/javax/swing/text/DefaultFormatter.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/javax/swing/text/DefaultFormatter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -24,6 +24,8 @@
  */
 package javax.swing.text;
 
+import sun.reflect.misc.ConstructorUtil;
+
 import java.io.Serializable;
 import java.lang.reflect.*;
 import java.text.ParseException;
@@ -245,7 +247,7 @@
             Constructor cons;
 
             try {
-                cons = vc.getConstructor(new Class[] { String.class });
+                cons = ConstructorUtil.getConstructor(vc, new Class[]{String.class});
 
             } catch (NoSuchMethodException nsme) {
                 cons = null;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/AnnotationVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,186 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A visitor to visit a Java annotation. The methods of this class must be
+ * called in the following order: ( <tt>visit</tt> | <tt>visitEnum</tt> |
+ * <tt>visitAnnotation</tt> | <tt>visitArray</tt> )* <tt>visitEnd</tt>.
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+public abstract class AnnotationVisitor {
+
+    /**
+     * The ASM API version implemented by this visitor. The value of this field
+     * must be one of {@link Opcodes#ASM4}.
+     */
+    protected final int api;
+
+    /**
+     * The annotation visitor to which this visitor must delegate method calls.
+     * May be null.
+     */
+    protected AnnotationVisitor av;
+
+    /**
+     * Constructs a new {@link AnnotationVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public AnnotationVisitor(final int api) {
+        this(api, null);
+    }
+
+    /**
+     * Constructs a new {@link AnnotationVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param av the annotation visitor to which this visitor must delegate
+     *        method calls. May be null.
+     */
+    public AnnotationVisitor(final int api, final AnnotationVisitor av) {
+        /*if (api != Opcodes.ASM4) {
+            throw new IllegalArgumentException();
+        }*/
+        this.api = api;
+        this.av = av;
+    }
+
+    /**
+     * Visits a primitive value of the annotation.
+     *
+     * @param name the value name.
+     * @param value the actual value, whose type must be {@link Byte},
+     *        {@link Boolean}, {@link Character}, {@link Short}, {@link Integer}
+     *        , {@link Long}, {@link Float}, {@link Double}, {@link String} or
+     *        {@link Type} or OBJECT or ARRAY sort. This value can also be an
+     *        array of byte, boolean, short, char, int, long, float or double
+     *        values (this is equivalent to using {@link #visitArray visitArray}
+     *        and visiting each array element in turn, but is more convenient).
+     */
+    public void visit(String name, Object value) {
+        if (av != null) {
+            av.visit(name, value);
+        }
+    }
+
+    /**
+     * Visits an enumeration value of the annotation.
+     *
+     * @param name the value name.
+     * @param desc the class descriptor of the enumeration class.
+     * @param value the actual enumeration value.
+     */
+    public void visitEnum(String name, String desc, String value) {
+        if (av != null) {
+            av.visitEnum(name, desc, value);
+        }
+    }
+
+    /**
+     * Visits a nested annotation value of the annotation.
+     *
+     * @param name the value name.
+     * @param desc the class descriptor of the nested annotation class.
+     * @return a visitor to visit the actual nested annotation value, or
+     *         <tt>null</tt> if this visitor is not interested in visiting
+     *         this nested annotation. <i>The nested annotation value must be
+     *         fully visited before calling other methods on this annotation
+     *         visitor</i>.
+     */
+    public AnnotationVisitor visitAnnotation(String name, String desc) {
+        if (av != null) {
+            return av.visitAnnotation(name, desc);
+        }
+        return null;
+    }
+
+    /**
+     * Visits an array value of the annotation. Note that arrays of primitive
+     * types (such as byte, boolean, short, char, int, long, float or double)
+     * can be passed as value to {@link #visit visit}. This is what
+     * {@link ClassReader} does.
+     *
+     * @param name the value name.
+     * @return a visitor to visit the actual array value elements, or
+     *         <tt>null</tt> if this visitor is not interested in visiting
+     *         these values. The 'name' parameters passed to the methods of this
+     *         visitor are ignored. <i>All the array values must be visited
+     *         before calling other methods on this annotation visitor</i>.
+     */
+    public AnnotationVisitor visitArray(String name) {
+        if (av != null) {
+            return av.visitArray(name);
+        }
+        return null;
+    }
+
+    /**
+     * Visits the end of the annotation.
+     */
+    public void visitEnd() {
+        if (av != null) {
+            av.visitEnd();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/AnnotationWriter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,351 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * An {@link AnnotationVisitor} that generates annotations in bytecode form.
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+final class AnnotationWriter extends AnnotationVisitor {
+
+    /**
+     * The class writer to which this annotation must be added.
+     */
+    private final ClassWriter cw;
+
+    /**
+     * The number of values in this annotation.
+     */
+    private int size;
+
+    /**
+     * <tt>true<tt> if values are named, <tt>false</tt> otherwise. Annotation
+     * writers used for annotation default and annotation arrays use unnamed
+     * values.
+     */
+    private final boolean named;
+
+    /**
+     * The annotation values in bytecode form. This byte vector only contains
+     * the values themselves, i.e. the number of values must be stored as a
+     * unsigned short just before these bytes.
+     */
+    private final ByteVector bv;
+
+    /**
+     * The byte vector to be used to store the number of values of this
+     * annotation. See {@link #bv}.
+     */
+    private final ByteVector parent;
+
+    /**
+     * Where the number of values of this annotation must be stored in
+     * {@link #parent}.
+     */
+    private final int offset;
+
+    /**
+     * Next annotation writer. This field is used to store annotation lists.
+     */
+    AnnotationWriter next;
+
+    /**
+     * Previous annotation writer. This field is used to store annotation lists.
+     */
+    AnnotationWriter prev;
+
+    // ------------------------------------------------------------------------
+    // Constructor
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a new {@link AnnotationWriter}.
+     *
+     * @param cw the class writer to which this annotation must be added.
+     * @param named <tt>true<tt> if values are named, <tt>false</tt> otherwise.
+     * @param bv where the annotation values must be stored.
+     * @param parent where the number of annotation values must be stored.
+     * @param offset where in <tt>parent</tt> the number of annotation values must
+     *      be stored.
+     */
+    AnnotationWriter(
+        final ClassWriter cw,
+        final boolean named,
+        final ByteVector bv,
+        final ByteVector parent,
+        final int offset)
+    {
+        super(Opcodes.ASM4);
+        this.cw = cw;
+        this.named = named;
+        this.bv = bv;
+        this.parent = parent;
+        this.offset = offset;
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the AnnotationVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(final String name, final Object value) {
+        ++size;
+        if (named) {
+            bv.putShort(cw.newUTF8(name));
+        }
+        if (value instanceof String) {
+            bv.put12('s', cw.newUTF8((String) value));
+        } else if (value instanceof Byte) {
+            bv.put12('B', cw.newInteger(((Byte) value).byteValue()).index);
+        } else if (value instanceof Boolean) {
+            int v = ((Boolean) value).booleanValue() ? 1 : 0;
+            bv.put12('Z', cw.newInteger(v).index);
+        } else if (value instanceof Character) {
+            bv.put12('C', cw.newInteger(((Character) value).charValue()).index);
+        } else if (value instanceof Short) {
+            bv.put12('S', cw.newInteger(((Short) value).shortValue()).index);
+        } else if (value instanceof Type) {
+            bv.put12('c', cw.newUTF8(((Type) value).getDescriptor()));
+        } else if (value instanceof byte[]) {
+            byte[] v = (byte[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('B', cw.newInteger(v[i]).index);
+            }
+        } else if (value instanceof boolean[]) {
+            boolean[] v = (boolean[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('Z', cw.newInteger(v[i] ? 1 : 0).index);
+            }
+        } else if (value instanceof short[]) {
+            short[] v = (short[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('S', cw.newInteger(v[i]).index);
+            }
+        } else if (value instanceof char[]) {
+            char[] v = (char[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('C', cw.newInteger(v[i]).index);
+            }
+        } else if (value instanceof int[]) {
+            int[] v = (int[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('I', cw.newInteger(v[i]).index);
+            }
+        } else if (value instanceof long[]) {
+            long[] v = (long[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('J', cw.newLong(v[i]).index);
+            }
+        } else if (value instanceof float[]) {
+            float[] v = (float[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('F', cw.newFloat(v[i]).index);
+            }
+        } else if (value instanceof double[]) {
+            double[] v = (double[]) value;
+            bv.put12('[', v.length);
+            for (int i = 0; i < v.length; i++) {
+                bv.put12('D', cw.newDouble(v[i]).index);
+            }
+        } else {
+            Item i = cw.newConstItem(value);
+            bv.put12(".s.IFJDCS".charAt(i.type), i.index);
+        }
+    }
+
+    @Override
+    public void visitEnum(
+        final String name,
+        final String desc,
+        final String value)
+    {
+        ++size;
+        if (named) {
+            bv.putShort(cw.newUTF8(name));
+        }
+        bv.put12('e', cw.newUTF8(desc)).putShort(cw.newUTF8(value));
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String name,
+        final String desc)
+    {
+        ++size;
+        if (named) {
+            bv.putShort(cw.newUTF8(name));
+        }
+        // write tag and type, and reserve space for values count
+        bv.put12('@', cw.newUTF8(desc)).putShort(0);
+        return new AnnotationWriter(cw, true, bv, bv, bv.length - 2);
+    }
+
+    @Override
+    public AnnotationVisitor visitArray(final String name) {
+        ++size;
+        if (named) {
+            bv.putShort(cw.newUTF8(name));
+        }
+        // write tag, and reserve space for array size
+        bv.put12('[', 0);
+        return new AnnotationWriter(cw, false, bv, bv, bv.length - 2);
+    }
+
+    @Override
+    public void visitEnd() {
+        if (parent != null) {
+            byte[] data = parent.data;
+            data[offset] = (byte) (size >>> 8);
+            data[offset + 1] = (byte) size;
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the size of this annotation writer list.
+     *
+     * @return the size of this annotation writer list.
+     */
+    int getSize() {
+        int size = 0;
+        AnnotationWriter aw = this;
+        while (aw != null) {
+            size += aw.bv.length;
+            aw = aw.next;
+        }
+        return size;
+    }
+
+    /**
+     * Puts the annotations of this annotation writer list into the given byte
+     * vector.
+     *
+     * @param out where the annotations must be put.
+     */
+    void put(final ByteVector out) {
+        int n = 0;
+        int size = 2;
+        AnnotationWriter aw = this;
+        AnnotationWriter last = null;
+        while (aw != null) {
+            ++n;
+            size += aw.bv.length;
+            aw.visitEnd(); // in case user forgot to call visitEnd
+            aw.prev = last;
+            last = aw;
+            aw = aw.next;
+        }
+        out.putInt(size);
+        out.putShort(n);
+        aw = last;
+        while (aw != null) {
+            out.putByteArray(aw.bv.data, 0, aw.bv.length);
+            aw = aw.prev;
+        }
+    }
+
+    /**
+     * Puts the given annotation lists into the given byte vector.
+     *
+     * @param panns an array of annotation writer lists.
+     * @param off index of the first annotation to be written.
+     * @param out where the annotations must be put.
+     */
+    static void put(
+        final AnnotationWriter[] panns,
+        final int off,
+        final ByteVector out)
+    {
+        int size = 1 + 2 * (panns.length - off);
+        for (int i = off; i < panns.length; ++i) {
+            size += panns[i] == null ? 0 : panns[i].getSize();
+        }
+        out.putInt(size).putByte(panns.length - off);
+        for (int i = off; i < panns.length; ++i) {
+            AnnotationWriter aw = panns[i];
+            AnnotationWriter last = null;
+            int n = 0;
+            while (aw != null) {
+                ++n;
+                aw.visitEnd(); // in case user forgot to call visitEnd
+                aw.prev = last;
+                last = aw;
+                aw = aw.next;
+            }
+            out.putShort(n);
+            aw = last;
+            while (aw != null) {
+                out.putByteArray(aw.bv.data, 0, aw.bv.length);
+                aw = aw.prev;
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Attribute.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,283 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A non standard class, field, method or code attribute.
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+public class Attribute {
+
+    /**
+     * The type of this attribute.
+     */
+    public final String type;
+
+    /**
+     * The raw value of this attribute, used only for unknown attributes.
+     */
+    byte[] value;
+
+    /**
+     * The next attribute in this attribute list. May be <tt>null</tt>.
+     */
+    Attribute next;
+
+    /**
+     * Constructs a new empty attribute.
+     *
+     * @param type the type of the attribute.
+     */
+    protected Attribute(final String type) {
+        this.type = type;
+    }
+
+    /**
+     * Returns <tt>true</tt> if this type of attribute is unknown. The default
+     * implementation of this method always returns <tt>true</tt>.
+     *
+     * @return <tt>true</tt> if this type of attribute is unknown.
+     */
+    public boolean isUnknown() {
+        return true;
+    }
+
+    /**
+     * Returns <tt>true</tt> if this type of attribute is a code attribute.
+     *
+     * @return <tt>true</tt> if this type of attribute is a code attribute.
+     */
+    public boolean isCodeAttribute() {
+        return false;
+    }
+
+    /**
+     * Returns the labels corresponding to this attribute.
+     *
+     * @return the labels corresponding to this attribute, or <tt>null</tt> if
+     *         this attribute is not a code attribute that contains labels.
+     */
+    protected Label[] getLabels() {
+        return null;
+    }
+
+    /**
+     * Reads a {@link #type type} attribute. This method must return a <i>new</i>
+     * {@link Attribute} object, of type {@link #type type}, corresponding to
+     * the <tt>len</tt> bytes starting at the given offset, in the given class
+     * reader.
+     *
+     * @param cr the class that contains the attribute to be read.
+     * @param off index of the first byte of the attribute's content in {@link
+     *        ClassReader#b cr.b}. The 6 attribute header bytes, containing the
+     *        type and the length of the attribute, are not taken into account
+     *        here.
+     * @param len the length of the attribute's content.
+     * @param buf buffer to be used to call
+     *        {@link ClassReader#readUTF8 readUTF8},
+     *        {@link ClassReader#readClass(int,char[]) readClass} or
+     *        {@link ClassReader#readConst readConst}.
+     * @param codeOff index of the first byte of code's attribute content in
+     *        {@link ClassReader#b cr.b}, or -1 if the attribute to be read is
+     *        not a code attribute. The 6 attribute header bytes, containing the
+     *        type and the length of the attribute, are not taken into account
+     *        here.
+     * @param labels the labels of the method's code, or <tt>null</tt> if the
+     *        attribute to be read is not a code attribute.
+     * @return a <i>new</i> {@link Attribute} object corresponding to the given
+     *         bytes.
+     */
+    protected Attribute read(
+        final ClassReader cr,
+        final int off,
+        final int len,
+        final char[] buf,
+        final int codeOff,
+        final Label[] labels)
+    {
+        Attribute attr = new Attribute(type);
+        attr.value = new byte[len];
+        System.arraycopy(cr.b, off, attr.value, 0, len);
+        return attr;
+    }
+
+    /**
+     * Returns the byte array form of this attribute.
+     *
+     * @param cw the class to which this attribute must be added. This parameter
+     *        can be used to add to the constant pool of this class the items
+     *        that corresponds to this attribute.
+     * @param code the bytecode of the method corresponding to this code
+     *        attribute, or <tt>null</tt> if this attribute is not a code
+     *        attributes.
+     * @param len the length of the bytecode of the method corresponding to this
+     *        code attribute, or <tt>null</tt> if this attribute is not a code
+     *        attribute.
+     * @param maxStack the maximum stack size of the method corresponding to
+     *        this code attribute, or -1 if this attribute is not a code
+     *        attribute.
+     * @param maxLocals the maximum number of local variables of the method
+     *        corresponding to this code attribute, or -1 if this attribute is
+     *        not a code attribute.
+     * @return the byte array form of this attribute.
+     */
+    protected ByteVector write(
+        final ClassWriter cw,
+        final byte[] code,
+        final int len,
+        final int maxStack,
+        final int maxLocals)
+    {
+        ByteVector v = new ByteVector();
+        v.data = value;
+        v.length = value.length;
+        return v;
+    }
+
+    /**
+     * Returns the length of the attribute list that begins with this attribute.
+     *
+     * @return the length of the attribute list that begins with this attribute.
+     */
+    final int getCount() {
+        int count = 0;
+        Attribute attr = this;
+        while (attr != null) {
+            count += 1;
+            attr = attr.next;
+        }
+        return count;
+    }
+
+    /**
+     * Returns the size of all the attributes in this attribute list.
+     *
+     * @param cw the class writer to be used to convert the attributes into byte
+     *        arrays, with the {@link #write write} method.
+     * @param code the bytecode of the method corresponding to these code
+     *        attributes, or <tt>null</tt> if these attributes are not code
+     *        attributes.
+     * @param len the length of the bytecode of the method corresponding to
+     *        these code attributes, or <tt>null</tt> if these attributes are
+     *        not code attributes.
+     * @param maxStack the maximum stack size of the method corresponding to
+     *        these code attributes, or -1 if these attributes are not code
+     *        attributes.
+     * @param maxLocals the maximum number of local variables of the method
+     *        corresponding to these code attributes, or -1 if these attributes
+     *        are not code attributes.
+     * @return the size of all the attributes in this attribute list. This size
+     *         includes the size of the attribute headers.
+     */
+    final int getSize(
+        final ClassWriter cw,
+        final byte[] code,
+        final int len,
+        final int maxStack,
+        final int maxLocals)
+    {
+        Attribute attr = this;
+        int size = 0;
+        while (attr != null) {
+            cw.newUTF8(attr.type);
+            size += attr.write(cw, code, len, maxStack, maxLocals).length + 6;
+            attr = attr.next;
+        }
+        return size;
+    }
+
+    /**
+     * Writes all the attributes of this attribute list in the given byte
+     * vector.
+     *
+     * @param cw the class writer to be used to convert the attributes into byte
+     *        arrays, with the {@link #write write} method.
+     * @param code the bytecode of the method corresponding to these code
+     *        attributes, or <tt>null</tt> if these attributes are not code
+     *        attributes.
+     * @param len the length of the bytecode of the method corresponding to
+     *        these code attributes, or <tt>null</tt> if these attributes are
+     *        not code attributes.
+     * @param maxStack the maximum stack size of the method corresponding to
+     *        these code attributes, or -1 if these attributes are not code
+     *        attributes.
+     * @param maxLocals the maximum number of local variables of the method
+     *        corresponding to these code attributes, or -1 if these attributes
+     *        are not code attributes.
+     * @param out where the attributes must be written.
+     */
+    final void put(
+        final ClassWriter cw,
+        final byte[] code,
+        final int len,
+        final int maxStack,
+        final int maxLocals,
+        final ByteVector out)
+    {
+        Attribute attr = this;
+        while (attr != null) {
+            ByteVector b = attr.write(cw, code, len, maxStack, maxLocals);
+            out.putShort(cw.newUTF8(attr.type)).putInt(b.length);
+            out.putByteArray(b.data, 0, b.length);
+            attr = attr.next;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/ByteVector.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,322 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A dynamically extensible vector of bytes. This class is roughly equivalent to
+ * a DataOutputStream on top of a ByteArrayOutputStream, but is more efficient.
+ *
+ * @author Eric Bruneton
+ */
+public class ByteVector {
+
+    /**
+     * The content of this vector.
+     */
+    byte[] data;
+
+    /**
+     * Actual number of bytes in this vector.
+     */
+    int length;
+
+    /**
+     * Constructs a new {@link ByteVector ByteVector} with a default initial
+     * size.
+     */
+    public ByteVector() {
+        data = new byte[64];
+    }
+
+    /**
+     * Constructs a new {@link ByteVector ByteVector} with the given initial
+     * size.
+     *
+     * @param initialSize the initial size of the byte vector to be constructed.
+     */
+    public ByteVector(final int initialSize) {
+        data = new byte[initialSize];
+    }
+
+    /**
+     * Puts a byte into this byte vector. The byte vector is automatically
+     * enlarged if necessary.
+     *
+     * @param b a byte.
+     * @return this byte vector.
+     */
+    public ByteVector putByte(final int b) {
+        int length = this.length;
+        if (length + 1 > data.length) {
+            enlarge(1);
+        }
+        data[length++] = (byte) b;
+        this.length = length;
+        return this;
+    }
+
+    /**
+     * Puts two bytes into this byte vector. The byte vector is automatically
+     * enlarged if necessary.
+     *
+     * @param b1 a byte.
+     * @param b2 another byte.
+     * @return this byte vector.
+     */
+    ByteVector put11(final int b1, final int b2) {
+        int length = this.length;
+        if (length + 2 > data.length) {
+            enlarge(2);
+        }
+        byte[] data = this.data;
+        data[length++] = (byte) b1;
+        data[length++] = (byte) b2;
+        this.length = length;
+        return this;
+    }
+
+    /**
+     * Puts a short into this byte vector. The byte vector is automatically
+     * enlarged if necessary.
+     *
+     * @param s a short.
+     * @return this byte vector.
+     */
+    public ByteVector putShort(final int s) {
+        int length = this.length;
+        if (length + 2 > data.length) {
+            enlarge(2);
+        }
+        byte[] data = this.data;
+        data[length++] = (byte) (s >>> 8);
+        data[length++] = (byte) s;
+        this.length = length;
+        return this;
+    }
+
+    /**
+     * Puts a byte and a short into this byte vector. The byte vector is
+     * automatically enlarged if necessary.
+     *
+     * @param b a byte.
+     * @param s a short.
+     * @return this byte vector.
+     */
+    ByteVector put12(final int b, final int s) {
+        int length = this.length;
+        if (length + 3 > data.length) {
+            enlarge(3);
+        }
+        byte[] data = this.data;
+        data[length++] = (byte) b;
+        data[length++] = (byte) (s >>> 8);
+        data[length++] = (byte) s;
+        this.length = length;
+        return this;
+    }
+
+    /**
+     * Puts an int into this byte vector. The byte vector is automatically
+     * enlarged if necessary.
+     *
+     * @param i an int.
+     * @return this byte vector.
+     */
+    public ByteVector putInt(final int i) {
+        int length = this.length;
+        if (length + 4 > data.length) {
+            enlarge(4);
+        }
+        byte[] data = this.data;
+        data[length++] = (byte) (i >>> 24);
+        data[length++] = (byte) (i >>> 16);
+        data[length++] = (byte) (i >>> 8);
+        data[length++] = (byte) i;
+        this.length = length;
+        return this;
+    }
+
+    /**
+     * Puts a long into this byte vector. The byte vector is automatically
+     * enlarged if necessary.
+     *
+     * @param l a long.
+     * @return this byte vector.
+     */
+    public ByteVector putLong(final long l) {
+        int length = this.length;
+        if (length + 8 > data.length) {
+            enlarge(8);
+        }
+        byte[] data = this.data;
+        int i = (int) (l >>> 32);
+        data[length++] = (byte) (i >>> 24);
+        data[length++] = (byte) (i >>> 16);
+        data[length++] = (byte) (i >>> 8);
+        data[length++] = (byte) i;
+        i = (int) l;
+        data[length++] = (byte) (i >>> 24);
+        data[length++] = (byte) (i >>> 16);
+        data[length++] = (byte) (i >>> 8);
+        data[length++] = (byte) i;
+        this.length = length;
+        return this;
+    }
+
+    /**
+     * Puts an UTF8 string into this byte vector. The byte vector is
+     * automatically enlarged if necessary.
+     *
+     * @param s a String.
+     * @return this byte vector.
+     */
+    public ByteVector putUTF8(final String s) {
+        int charLength = s.length();
+        int len = length;
+        if (len + 2 + charLength > data.length) {
+            enlarge(2 + charLength);
+        }
+        byte[] data = this.data;
+        // optimistic algorithm: instead of computing the byte length and then
+        // serializing the string (which requires two loops), we assume the byte
+        // length is equal to char length (which is the most frequent case), and
+        // we start serializing the string right away. During the serialization,
+        // if we find that this assumption is wrong, we continue with the
+        // general method.
+        data[len++] = (byte) (charLength >>> 8);
+        data[len++] = (byte) charLength;
+        for (int i = 0; i < charLength; ++i) {
+            char c = s.charAt(i);
+            if (c >= '\001' && c <= '\177') {
+                data[len++] = (byte) c;
+            } else {
+                int byteLength = i;
+                for (int j = i; j < charLength; ++j) {
+                    c = s.charAt(j);
+                    if (c >= '\001' && c <= '\177') {
+                        byteLength++;
+                    } else if (c > '\u07FF') {
+                        byteLength += 3;
+                    } else {
+                        byteLength += 2;
+                    }
+                }
+                data[length] = (byte) (byteLength >>> 8);
+                data[length + 1] = (byte) byteLength;
+                if (length + 2 + byteLength > data.length) {
+                    length = len;
+                    enlarge(2 + byteLength);
+                    data = this.data;
+                }
+                for (int j = i; j < charLength; ++j) {
+                    c = s.charAt(j);
+                    if (c >= '\001' && c <= '\177') {
+                        data[len++] = (byte) c;
+                    } else if (c > '\u07FF') {
+                        data[len++] = (byte) (0xE0 | c >> 12 & 0xF);
+                        data[len++] = (byte) (0x80 | c >> 6 & 0x3F);
+                        data[len++] = (byte) (0x80 | c & 0x3F);
+                    } else {
+                        data[len++] = (byte) (0xC0 | c >> 6 & 0x1F);
+                        data[len++] = (byte) (0x80 | c & 0x3F);
+                    }
+                }
+                break;
+            }
+        }
+        length = len;
+        return this;
+    }
+
+    /**
+     * Puts an array of bytes into this byte vector. The byte vector is
+     * automatically enlarged if necessary.
+     *
+     * @param b an array of bytes. May be <tt>null</tt> to put <tt>len</tt>
+     *        null bytes into this byte vector.
+     * @param off index of the fist byte of b that must be copied.
+     * @param len number of bytes of b that must be copied.
+     * @return this byte vector.
+     */
+    public ByteVector putByteArray(final byte[] b, final int off, final int len)
+    {
+        if (length + len > data.length) {
+            enlarge(len);
+        }
+        if (b != null) {
+            System.arraycopy(b, off, data, length, len);
+        }
+        length += len;
+        return this;
+    }
+
+    /**
+     * Enlarge this byte vector so that it can receive n more bytes.
+     *
+     * @param size number of additional bytes that this byte vector should be
+     *        able to receive.
+     */
+    private void enlarge(final int size) {
+        int length1 = 2 * data.length;
+        int length2 = length + size;
+        byte[] newData = new byte[length1 > length2 ? length1 : length2];
+        System.arraycopy(data, 0, newData, 0, length);
+        data = newData;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/ClassReader.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,2245 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+/**
+ * A Java class parser to make a {@link ClassVisitor} visit an existing class.
+ * This class parses a byte array conforming to the Java class file format and
+ * calls the appropriate visit methods of a given class visitor for each field,
+ * method and bytecode instruction encountered.
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+public class ClassReader {
+
+    /**
+     * True to enable signatures support.
+     */
+    static final boolean SIGNATURES = true;
+
+    /**
+     * True to enable annotations support.
+     */
+    static final boolean ANNOTATIONS = true;
+
+    /**
+     * True to enable stack map frames support.
+     */
+    static final boolean FRAMES = true;
+
+    /**
+     * True to enable bytecode writing support.
+     */
+    static final boolean WRITER = true;
+
+    /**
+     * True to enable JSR_W and GOTO_W support.
+     */
+    static final boolean RESIZE = true;
+
+    /**
+     * Flag to skip method code. If this class is set <code>CODE</code>
+     * attribute won't be visited. This can be used, for example, to retrieve
+     * annotations for methods and method parameters.
+     */
+    public static final int SKIP_CODE = 1;
+
+    /**
+     * Flag to skip the debug information in the class. If this flag is set the
+     * debug information of the class is not visited, i.e. the
+     * {@link MethodVisitor#visitLocalVariable visitLocalVariable} and
+     * {@link MethodVisitor#visitLineNumber visitLineNumber} methods will not be
+     * called.
+     */
+    public static final int SKIP_DEBUG = 2;
+
+    /**
+     * Flag to skip the stack map frames in the class. If this flag is set the
+     * stack map frames of the class is not visited, i.e. the
+     * {@link MethodVisitor#visitFrame visitFrame} method will not be called.
+     * This flag is useful when the {@link ClassWriter#COMPUTE_FRAMES} option is
+     * used: it avoids visiting frames that will be ignored and recomputed from
+     * scratch in the class writer.
+     */
+    public static final int SKIP_FRAMES = 4;
+
+    /**
+     * Flag to expand the stack map frames. By default stack map frames are
+     * visited in their original format (i.e. "expanded" for classes whose
+     * version is less than V1_6, and "compressed" for the other classes). If
+     * this flag is set, stack map frames are always visited in expanded format
+     * (this option adds a decompression/recompression step in ClassReader and
+     * ClassWriter which degrades performances quite a lot).
+     */
+    public static final int EXPAND_FRAMES = 8;
+
+    /**
+     * The class to be parsed. <i>The content of this array must not be
+     * modified. This field is intended for {@link Attribute} sub classes, and
+     * is normally not needed by class generators or adapters.</i>
+     */
+    public final byte[] b;
+
+    /**
+     * The start index of each constant pool item in {@link #b b}, plus one.
+     * The one byte offset skips the constant pool item tag that indicates its
+     * type.
+     */
+    private final int[] items;
+
+    /**
+     * The String objects corresponding to the CONSTANT_Utf8 items. This cache
+     * avoids multiple parsing of a given CONSTANT_Utf8 constant pool item,
+     * which GREATLY improves performances (by a factor 2 to 3). This caching
+     * strategy could be extended to all constant pool items, but its benefit
+     * would not be so great for these items (because they are much less
+     * expensive to parse than CONSTANT_Utf8 items).
+     */
+    private final String[] strings;
+
+    /**
+     * Maximum length of the strings contained in the constant pool of the
+     * class.
+     */
+    private final int maxStringLength;
+
+    /**
+     * Start index of the class header information (access, name...) in
+     * {@link #b b}.
+     */
+    public final int header;
+
+    // ------------------------------------------------------------------------
+    // Constructors
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a new {@link ClassReader} object.
+     *
+     * @param b the bytecode of the class to be read.
+     */
+    public ClassReader(final byte[] b) {
+        this(b, 0, b.length);
+    }
+
+    /**
+     * Constructs a new {@link ClassReader} object.
+     *
+     * @param b the bytecode of the class to be read.
+     * @param off the start offset of the class data.
+     * @param len the length of the class data.
+     */
+    public ClassReader(final byte[] b, final int off, final int len) {
+        this.b = b;
+        // checks the class version
+        if (readShort(6) > Opcodes.V1_7) {
+            throw new IllegalArgumentException();
+        }
+        // parses the constant pool
+        items = new int[readUnsignedShort(off + 8)];
+        int n = items.length;
+        strings = new String[n];
+        int max = 0;
+        int index = off + 10;
+        for (int i = 1; i < n; ++i) {
+            items[i] = index + 1;
+            int size;
+            switch (b[index]) {
+                case ClassWriter.FIELD:
+                case ClassWriter.METH:
+                case ClassWriter.IMETH:
+                case ClassWriter.INT:
+                case ClassWriter.FLOAT:
+                case ClassWriter.NAME_TYPE:
+                case ClassWriter.INDY:
+                    size = 5;
+                    break;
+                case ClassWriter.LONG:
+                case ClassWriter.DOUBLE:
+                    size = 9;
+                    ++i;
+                    break;
+                case ClassWriter.UTF8:
+                    size = 3 + readUnsignedShort(index + 1);
+                    if (size > max) {
+                        max = size;
+                    }
+                    break;
+                case ClassWriter.HANDLE:
+                    size = 4;
+                    break;
+                // case ClassWriter.CLASS:
+                // case ClassWriter.STR:
+                // case ClassWriter.MTYPE
+                default:
+                    size = 3;
+                    break;
+            }
+            index += size;
+        }
+        maxStringLength = max;
+        // the class header information starts just after the constant pool
+        header = index;
+    }
+
+    /**
+     * Returns the class's access flags (see {@link Opcodes}). This value may
+     * not reflect Deprecated and Synthetic flags when bytecode is before 1.5
+     * and those flags are represented by attributes.
+     *
+     * @return the class access flags
+     *
+     * @see ClassVisitor#visit(int, int, String, String, String, String[])
+     */
+    public int getAccess() {
+        return readUnsignedShort(header);
+    }
+
+    /**
+     * Returns the internal name of the class (see
+     * {@link Type#getInternalName() getInternalName}).
+     *
+     * @return the internal class name
+     *
+     * @see ClassVisitor#visit(int, int, String, String, String, String[])
+     */
+    public String getClassName() {
+        return readClass(header + 2, new char[maxStringLength]);
+    }
+
+    /**
+     * Returns the internal of name of the super class (see
+     * {@link Type#getInternalName() getInternalName}). For interfaces, the
+     * super class is {@link Object}.
+     *
+     * @return the internal name of super class, or <tt>null</tt> for
+     *         {@link Object} class.
+     *
+     * @see ClassVisitor#visit(int, int, String, String, String, String[])
+     */
+    public String getSuperName() {
+        int n = items[readUnsignedShort(header + 4)];
+        return n == 0 ? null : readUTF8(n, new char[maxStringLength]);
+    }
+
+    /**
+     * Returns the internal names of the class's interfaces (see
+     * {@link Type#getInternalName() getInternalName}).
+     *
+     * @return the array of internal names for all implemented interfaces or
+     *         <tt>null</tt>.
+     *
+     * @see ClassVisitor#visit(int, int, String, String, String, String[])
+     */
+    public String[] getInterfaces() {
+        int index = header + 6;
+        int n = readUnsignedShort(index);
+        String[] interfaces = new String[n];
+        if (n > 0) {
+            char[] buf = new char[maxStringLength];
+            for (int i = 0; i < n; ++i) {
+                index += 2;
+                interfaces[i] = readClass(index, buf);
+            }
+        }
+        return interfaces;
+    }
+
+    /**
+     * Copies the constant pool data into the given {@link ClassWriter}. Should
+     * be called before the {@link #accept(ClassVisitor,int)} method.
+     *
+     * @param classWriter the {@link ClassWriter} to copy constant pool into.
+     */
+    void copyPool(final ClassWriter classWriter) {
+        char[] buf = new char[maxStringLength];
+        int ll = items.length;
+        Item[] items2 = new Item[ll];
+        for (int i = 1; i < ll; i++) {
+            int index = items[i];
+            int tag = b[index - 1];
+            Item item = new Item(i);
+            int nameType;
+            switch (tag) {
+                case ClassWriter.FIELD:
+                case ClassWriter.METH:
+                case ClassWriter.IMETH:
+                    nameType = items[readUnsignedShort(index + 2)];
+                    item.set(tag,
+                            readClass(index, buf),
+                            readUTF8(nameType, buf),
+                            readUTF8(nameType + 2, buf));
+                    break;
+
+                case ClassWriter.INT:
+                    item.set(readInt(index));
+                    break;
+
+                case ClassWriter.FLOAT:
+                    item.set(Float.intBitsToFloat(readInt(index)));
+                    break;
+
+                case ClassWriter.NAME_TYPE:
+                    item.set(tag,
+                            readUTF8(index, buf),
+                            readUTF8(index + 2, buf),
+                            null);
+                    break;
+
+                case ClassWriter.LONG:
+                    item.set(readLong(index));
+                    ++i;
+                    break;
+
+                case ClassWriter.DOUBLE:
+                    item.set(Double.longBitsToDouble(readLong(index)));
+                    ++i;
+                    break;
+
+                case ClassWriter.UTF8: {
+                    String s = strings[i];
+                    if (s == null) {
+                        index = items[i];
+                        s = strings[i] = readUTF(index + 2,
+                                readUnsignedShort(index),
+                                buf);
+                    }
+                    item.set(tag, s, null, null);
+                }
+                    break;
+
+                case ClassWriter.HANDLE: {
+                    int fieldOrMethodRef = items[readUnsignedShort(index + 1)];
+                    nameType = items[readUnsignedShort(fieldOrMethodRef + 2)];
+                    item.set(ClassWriter.HANDLE_BASE + readByte(index),
+                            readClass(fieldOrMethodRef, buf),
+                            readUTF8(nameType, buf),
+                            readUTF8(nameType + 2, buf));
+
+                }
+                    break;
+
+
+                case ClassWriter.INDY:
+                    if (classWriter.bootstrapMethods == null) {
+                        copyBootstrapMethods(classWriter, items2, buf);
+                    }
+                    nameType = items[readUnsignedShort(index + 2)];
+                    item.set(readUTF8(nameType, buf),
+                            readUTF8(nameType + 2, buf),
+                            readUnsignedShort(index));
+                    break;
+
+
+                // case ClassWriter.STR:
+                // case ClassWriter.CLASS:
+                // case ClassWriter.MTYPE
+                default:
+                    item.set(tag, readUTF8(index, buf), null, null);
+                    break;
+            }
+
+            int index2 = item.hashCode % items2.length;
+            item.next = items2[index2];
+            items2[index2] = item;
+        }
+
+        int off = items[1] - 1;
+        classWriter.pool.putByteArray(b, off, header - off);
+        classWriter.items = items2;
+        classWriter.threshold = (int) (0.75d * ll);
+        classWriter.index = ll;
+    }
+
+    private void copyBootstrapMethods(ClassWriter classWriter, Item[] items2, char[] buf) {
+        int i, j, k, u, v;
+
+        // skip class header
+        v = header;
+        v += 8 + (readUnsignedShort(v + 6) << 1);
+
+        // skips fields and methods
+        i = readUnsignedShort(v);
+        v += 2;
+        for (; i > 0; --i) {
+            j = readUnsignedShort(v + 6);
+            v += 8;
+            for (; j > 0; --j) {
+                v += 6 + readInt(v + 2);
+            }
+        }
+        i = readUnsignedShort(v);
+        v += 2;
+        for (; i > 0; --i) {
+            j = readUnsignedShort(v + 6);
+            v += 8;
+            for (; j > 0; --j) {
+                v += 6 + readInt(v + 2);
+            }
+        }
+
+        // read class attributes
+        i = readUnsignedShort(v);
+        v += 2;
+        for (; i > 0; --i) {
+            String attrName = readUTF8(v, buf);
+            int size = readInt(v + 2);
+            if ("BootstrapMethods".equals(attrName)) {
+                int boostrapMethodCount = readUnsignedShort(v + 6);
+                int x = v + 8;
+                for (j = 0; j < boostrapMethodCount; j++) {
+                    int hashCode = readConst(readUnsignedShort(x), buf).hashCode();
+                    k = readUnsignedShort(x + 2);
+                    u = x + 4;
+                    for(; k > 0; --k) {
+                        hashCode ^= readConst(readUnsignedShort(u), buf).hashCode();
+                        u += 2;
+                    }
+                    Item item = new Item(j);
+                    item.set(x - v - 8, hashCode & 0x7FFFFFFF);
+
+                    int index2 = item.hashCode % items2.length;
+                    item.next = items2[index2];
+                    items2[index2] = item;
+
+                    x = u;
+                }
+
+                classWriter.bootstrapMethodsCount = boostrapMethodCount;
+                ByteVector bootstrapMethods = new ByteVector(size + 62);
+                bootstrapMethods.putByteArray(b, v + 8, size - 2);
+                classWriter.bootstrapMethods = bootstrapMethods;
+                return;
+            }
+            v += 6 + size;
+        }
+
+        // we are in trouble !!!
+    }
+
+    /**
+     * Constructs a new {@link ClassReader} object.
+     *
+     * @param is an input stream from which to read the class.
+     * @throws IOException if a problem occurs during reading.
+     */
+    public ClassReader(final InputStream is) throws IOException {
+        this(readClass(is, false));
+    }
+
+    /**
+     * Constructs a new {@link ClassReader} object.
+     *
+     * @param name the binary qualified name of the class to be read.
+     * @throws IOException if an exception occurs during reading.
+     */
+    public ClassReader(final String name) throws IOException {
+        this(readClass(ClassLoader.getSystemResourceAsStream(name.replace('.', '/')
+                + ".class"), true));
+    }
+
+    /**
+     * Reads the bytecode of a class.
+     *
+     * @param is an input stream from which to read the class.
+     * @param close true to close the input stream after reading.
+     * @return the bytecode read from the given input stream.
+     * @throws IOException if a problem occurs during reading.
+     */
+    private static byte[] readClass(final InputStream is, boolean close)
+            throws IOException
+    {
+        if (is == null) {
+            throw new IOException("Class not found");
+        }
+        try {
+            byte[] b = new byte[is.available()];
+            int len = 0;
+            while (true) {
+                int n = is.read(b, len, b.length - len);
+                if (n == -1) {
+                    if (len < b.length) {
+                        byte[] c = new byte[len];
+                        System.arraycopy(b, 0, c, 0, len);
+                        b = c;
+                    }
+                    return b;
+                }
+                len += n;
+                if (len == b.length) {
+                    int last = is.read();
+                    if (last < 0) {
+                        return b;
+                    }
+                    byte[] c = new byte[b.length + 1000];
+                    System.arraycopy(b, 0, c, 0, len);
+                    c[len++] = (byte) last;
+                    b = c;
+                }
+            }
+        } finally {
+            if (close) {
+                is.close();
+            }
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Public methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Makes the given visitor visit the Java class of this {@link ClassReader}.
+     * This class is the one specified in the constructor (see
+     * {@link #ClassReader(byte[]) ClassReader}).
+     *
+     * @param classVisitor the visitor that must visit this class.
+     * @param flags option flags that can be used to modify the default behavior
+     *        of this class. See {@link #SKIP_DEBUG}, {@link #EXPAND_FRAMES},
+     *        {@link #SKIP_FRAMES}, {@link #SKIP_CODE}.
+     */
+    public void accept(final ClassVisitor classVisitor, final int flags) {
+        accept(classVisitor, new Attribute[0], flags);
+    }
+
+    /**
+     * Makes the given visitor visit the Java class of this {@link ClassReader}.
+     * This class is the one specified in the constructor (see
+     * {@link #ClassReader(byte[]) ClassReader}).
+     *
+     * @param classVisitor the visitor that must visit this class.
+     * @param attrs prototypes of the attributes that must be parsed during the
+     *        visit of the class. Any attribute whose type is not equal to the
+     *        type of one the prototypes will not be parsed: its byte array
+     *        value will be passed unchanged to the ClassWriter. <i>This may
+     *        corrupt it if this value contains references to the constant pool,
+     *        or has syntactic or semantic links with a class element that has
+     *        been transformed by a class adapter between the reader and the
+     *        writer</i>.
+     * @param flags option flags that can be used to modify the default behavior
+     *        of this class. See {@link #SKIP_DEBUG}, {@link #EXPAND_FRAMES},
+     *        {@link #SKIP_FRAMES}, {@link #SKIP_CODE}.
+     */
+    public void accept(
+        final ClassVisitor classVisitor,
+        final Attribute[] attrs,
+        final int flags)
+    {
+        byte[] b = this.b; // the bytecode array
+        char[] c = new char[maxStringLength]; // buffer used to read strings
+        int i, j, k; // loop variables
+        int u, v, w; // indexes in b
+        Attribute attr;
+
+        int access;
+        String name;
+        String desc;
+        String attrName;
+        String signature;
+        int anns = 0;
+        int ianns = 0;
+        Attribute cattrs = null;
+
+        // visits the header
+        u = header;
+        access = readUnsignedShort(u);
+        name = readClass(u + 2, c);
+        v = items[readUnsignedShort(u + 4)];
+        String superClassName = v == 0 ? null : readUTF8(v, c);
+        String[] implementedItfs = new String[readUnsignedShort(u + 6)];
+        w = 0;
+        u += 8;
+        for (i = 0; i < implementedItfs.length; ++i) {
+            implementedItfs[i] = readClass(u, c);
+            u += 2;
+        }
+
+        boolean skipCode = (flags & SKIP_CODE) != 0;
+        boolean skipDebug = (flags & SKIP_DEBUG) != 0;
+        boolean unzip = (flags & EXPAND_FRAMES) != 0;
+
+        // skips fields and methods
+        v = u;
+        i = readUnsignedShort(v);
+        v += 2;
+        for (; i > 0; --i) {
+            j = readUnsignedShort(v + 6);
+            v += 8;
+            for (; j > 0; --j) {
+                v += 6 + readInt(v + 2);
+            }
+        }
+        i = readUnsignedShort(v);
+        v += 2;
+        for (; i > 0; --i) {
+            j = readUnsignedShort(v + 6);
+            v += 8;
+            for (; j > 0; --j) {
+                v += 6 + readInt(v + 2);
+            }
+        }
+        // reads the class's attributes
+        signature = null;
+        String sourceFile = null;
+        String sourceDebug = null;
+        String enclosingOwner = null;
+        String enclosingName = null;
+        String enclosingDesc = null;
+        int[] bootstrapMethods = null;  // start indexed of the bsms
+
+        i = readUnsignedShort(v);
+        v += 2;
+        for (; i > 0; --i) {
+            attrName = readUTF8(v, c);
+            // tests are sorted in decreasing frequency order
+            // (based on frequencies observed on typical classes)
+            if ("SourceFile".equals(attrName)) {
+                sourceFile = readUTF8(v + 6, c);
+            } else if ("InnerClasses".equals(attrName)) {
+                w = v + 6;
+            } else if ("EnclosingMethod".equals(attrName)) {
+                enclosingOwner = readClass(v + 6, c);
+                int item = readUnsignedShort(v + 8);
+                if (item != 0) {
+                    enclosingName = readUTF8(items[item], c);
+                    enclosingDesc = readUTF8(items[item] + 2, c);
+                }
+            } else if (SIGNATURES && "Signature".equals(attrName)) {
+                signature = readUTF8(v + 6, c);
+            } else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName)) {
+                anns = v + 6;
+            } else if ("Deprecated".equals(attrName)) {
+                access |= Opcodes.ACC_DEPRECATED;
+            } else if ("Synthetic".equals(attrName)) {
+                access |= Opcodes.ACC_SYNTHETIC | ClassWriter.ACC_SYNTHETIC_ATTRIBUTE;
+            } else if ("SourceDebugExtension".equals(attrName)) {
+                int len = readInt(v + 2);
+                sourceDebug = readUTF(v + 6, len, new char[len]);
+            } else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName)) {
+                ianns = v + 6;
+            } else if ("BootstrapMethods".equals(attrName)) {
+                int boostrapMethodCount = readUnsignedShort(v + 6);
+                bootstrapMethods = new int[boostrapMethodCount];
+                int x = v + 8;
+                for (j = 0; j < boostrapMethodCount; j++) {
+                    bootstrapMethods[j] = x;
+                    x += 2 + readUnsignedShort(x + 2) << 1;
+                }
+            } else {
+                attr = readAttribute(attrs,
+                        attrName,
+                        v + 6,
+                        readInt(v + 2),
+                        c,
+                        -1,
+                        null);
+                if (attr != null) {
+                    attr.next = cattrs;
+                    cattrs = attr;
+                }
+            }
+            v += 6 + readInt(v + 2);
+        }
+        // calls the visit method
+        classVisitor.visit(readInt(4),
+                access,
+                name,
+                signature,
+                superClassName,
+                implementedItfs);
+
+        // calls the visitSource method
+        if (!skipDebug && (sourceFile != null || sourceDebug != null)) {
+            classVisitor.visitSource(sourceFile, sourceDebug);
+        }
+
+        // calls the visitOuterClass method
+        if (enclosingOwner != null) {
+            classVisitor.visitOuterClass(enclosingOwner,
+                    enclosingName,
+                    enclosingDesc);
+        }
+
+        // visits the class annotations
+        if (ANNOTATIONS) {
+            for (i = 1; i >= 0; --i) {
+                v = i == 0 ? ianns : anns;
+                if (v != 0) {
+                    j = readUnsignedShort(v);
+                    v += 2;
+                    for (; j > 0; --j) {
+                        v = readAnnotationValues(v + 2,
+                                c,
+                                true,
+                                classVisitor.visitAnnotation(readUTF8(v, c), i != 0));
+                    }
+                }
+            }
+        }
+
+        // visits the class attributes
+        while (cattrs != null) {
+            attr = cattrs.next;
+            cattrs.next = null;
+            classVisitor.visitAttribute(cattrs);
+            cattrs = attr;
+        }
+
+        // calls the visitInnerClass method
+        if (w != 0) {
+            i = readUnsignedShort(w);
+            w += 2;
+            for (; i > 0; --i) {
+                classVisitor.visitInnerClass(readUnsignedShort(w) == 0
+                        ? null
+                        : readClass(w, c), readUnsignedShort(w + 2) == 0
+                        ? null
+                        : readClass(w + 2, c), readUnsignedShort(w + 4) == 0
+                        ? null
+                        : readUTF8(w + 4, c), readUnsignedShort(w + 6));
+                w += 8;
+            }
+        }
+
+        // visits the fields
+        i = readUnsignedShort(u);
+        u += 2;
+        for (; i > 0; --i) {
+            access = readUnsignedShort(u);
+            name = readUTF8(u + 2, c);
+            desc = readUTF8(u + 4, c);
+            // visits the field's attributes and looks for a ConstantValue
+            // attribute
+            int fieldValueItem = 0;
+            signature = null;
+            anns = 0;
+            ianns = 0;
+            cattrs = null;
+
+            j = readUnsignedShort(u + 6);
+            u += 8;
+            for (; j > 0; --j) {
+                attrName = readUTF8(u, c);
+                // tests are sorted in decreasing frequency order
+                // (based on frequencies observed on typical classes)
+                if ("ConstantValue".equals(attrName)) {
+                    fieldValueItem = readUnsignedShort(u + 6);
+                } else if (SIGNATURES && "Signature".equals(attrName)) {
+                    signature = readUTF8(u + 6, c);
+                } else if ("Deprecated".equals(attrName)) {
+                    access |= Opcodes.ACC_DEPRECATED;
+                } else if ("Synthetic".equals(attrName)) {
+                    access |= Opcodes.ACC_SYNTHETIC  | ClassWriter.ACC_SYNTHETIC_ATTRIBUTE;
+                } else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName)) {
+                    anns = u + 6;
+                } else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName)) {
+                    ianns = u + 6;
+                } else {
+                    attr = readAttribute(attrs,
+                            attrName,
+                            u + 6,
+                            readInt(u + 2),
+                            c,
+                            -1,
+                            null);
+                    if (attr != null) {
+                        attr.next = cattrs;
+                        cattrs = attr;
+                    }
+                }
+                u += 6 + readInt(u + 2);
+            }
+            // visits the field
+            FieldVisitor fv = classVisitor.visitField(access,
+                    name,
+                    desc,
+                    signature,
+                    fieldValueItem == 0 ? null : readConst(fieldValueItem, c));
+            // visits the field annotations and attributes
+            if (fv != null) {
+                if (ANNOTATIONS) {
+                    for (j = 1; j >= 0; --j) {
+                        v = j == 0 ? ianns : anns;
+                        if (v != 0) {
+                            k = readUnsignedShort(v);
+                            v += 2;
+                            for (; k > 0; --k) {
+                                v = readAnnotationValues(v + 2,
+                                        c,
+                                        true,
+                                        fv.visitAnnotation(readUTF8(v, c), j != 0));
+                            }
+                        }
+                    }
+                }
+                while (cattrs != null) {
+                    attr = cattrs.next;
+                    cattrs.next = null;
+                    fv.visitAttribute(cattrs);
+                    cattrs = attr;
+                }
+                fv.visitEnd();
+            }
+        }
+
+        // visits the methods
+        i = readUnsignedShort(u);
+        u += 2;
+        for (; i > 0; --i) {
+            int u0 = u + 6;
+            access = readUnsignedShort(u);
+            name = readUTF8(u + 2, c);
+            desc = readUTF8(u + 4, c);
+            signature = null;
+            anns = 0;
+            ianns = 0;
+            int dann = 0;
+            int mpanns = 0;
+            int impanns = 0;
+            cattrs = null;
+            v = 0;
+            w = 0;
+
+            // looks for Code and Exceptions attributes
+            j = readUnsignedShort(u + 6);
+            u += 8;
+            for (; j > 0; --j) {
+                attrName = readUTF8(u, c);
+                int attrSize = readInt(u + 2);
+                u += 6;
+                // tests are sorted in decreasing frequency order
+                // (based on frequencies observed on typical classes)
+                if ("Code".equals(attrName)) {
+                    if (!skipCode) {
+                        v = u;
+                    }
+                } else if ("Exceptions".equals(attrName)) {
+                    w = u;
+                } else if (SIGNATURES && "Signature".equals(attrName)) {
+                    signature = readUTF8(u, c);
+                } else if ("Deprecated".equals(attrName)) {
+                    access |= Opcodes.ACC_DEPRECATED;
+                } else if (ANNOTATIONS && "RuntimeVisibleAnnotations".equals(attrName)) {
+                    anns = u;
+                } else if (ANNOTATIONS && "AnnotationDefault".equals(attrName)) {
+                    dann = u;
+                } else if ("Synthetic".equals(attrName)) {
+                    access |= Opcodes.ACC_SYNTHETIC | ClassWriter.ACC_SYNTHETIC_ATTRIBUTE;
+                } else if (ANNOTATIONS && "RuntimeInvisibleAnnotations".equals(attrName)) {
+                    ianns = u;
+                } else if (ANNOTATIONS && "RuntimeVisibleParameterAnnotations".equals(attrName))
+                {
+                    mpanns = u;
+                } else if (ANNOTATIONS && "RuntimeInvisibleParameterAnnotations".equals(attrName))
+                {
+                    impanns = u;
+                } else {
+                    attr = readAttribute(attrs,
+                            attrName,
+                            u,
+                            attrSize,
+                            c,
+                            -1,
+                            null);
+                    if (attr != null) {
+                        attr.next = cattrs;
+                        cattrs = attr;
+                    }
+                }
+                u += attrSize;
+            }
+            // reads declared exceptions
+            String[] exceptions;
+            if (w == 0) {
+                exceptions = null;
+            } else {
+                exceptions = new String[readUnsignedShort(w)];
+                w += 2;
+                for (j = 0; j < exceptions.length; ++j) {
+                    exceptions[j] = readClass(w, c);
+                    w += 2;
+                }
+            }
+
+            // visits the method's code, if any
+            MethodVisitor mv = classVisitor.visitMethod(access,
+                    name,
+                    desc,
+                    signature,
+                    exceptions);
+
+            if (mv != null) {
+                /*
+                 * if the returned MethodVisitor is in fact a MethodWriter, it
+                 * means there is no method adapter between the reader and the
+                 * writer. If, in addition, the writer's constant pool was
+                 * copied from this reader (mw.cw.cr == this), and the signature
+                 * and exceptions of the method have not been changed, then it
+                 * is possible to skip all visit events and just copy the
+                 * original code of the method to the writer (the access, name
+                 * and descriptor can have been changed, this is not important
+                 * since they are not copied as is from the reader).
+                 */
+                if (WRITER && mv instanceof MethodWriter) {
+                    MethodWriter mw = (MethodWriter) mv;
+                    if (mw.cw.cr == this) {
+                        if (signature == mw.signature) {
+                            boolean sameExceptions = false;
+                            if (exceptions == null) {
+                                sameExceptions = mw.exceptionCount == 0;
+                            } else {
+                                if (exceptions.length == mw.exceptionCount) {
+                                    sameExceptions = true;
+                                    for (j = exceptions.length - 1; j >= 0; --j)
+                                    {
+                                        w -= 2;
+                                        if (mw.exceptions[j] != readUnsignedShort(w))
+                                        {
+                                            sameExceptions = false;
+                                            break;
+                                        }
+                                    }
+                                }
+                            }
+                            if (sameExceptions) {
+                                /*
+                                 * we do not copy directly the code into
+                                 * MethodWriter to save a byte array copy
+                                 * operation. The real copy will be done in
+                                 * ClassWriter.toByteArray().
+                                 */
+                                mw.classReaderOffset = u0;
+                                mw.classReaderLength = u - u0;
+                                continue;
+                            }
+                        }
+                    }
+                }
+
+                if (ANNOTATIONS && dann != 0) {
+                    AnnotationVisitor dv = mv.visitAnnotationDefault();
+                    readAnnotationValue(dann, c, null, dv);
+                    if (dv != null) {
+                        dv.visitEnd();
+                    }
+                }
+                if (ANNOTATIONS) {
+                    for (j = 1; j >= 0; --j) {
+                        w = j == 0 ? ianns : anns;
+                        if (w != 0) {
+                            k = readUnsignedShort(w);
+                            w += 2;
+                            for (; k > 0; --k) {
+                                w = readAnnotationValues(w + 2,
+                                        c,
+                                        true,
+                                        mv.visitAnnotation(readUTF8(w, c), j != 0));
+                            }
+                        }
+                    }
+                }
+                if (ANNOTATIONS && mpanns != 0) {
+                    readParameterAnnotations(mpanns, desc, c, true, mv);
+                }
+                if (ANNOTATIONS && impanns != 0) {
+                    readParameterAnnotations(impanns, desc, c, false, mv);
+                }
+                while (cattrs != null) {
+                    attr = cattrs.next;
+                    cattrs.next = null;
+                    mv.visitAttribute(cattrs);
+                    cattrs = attr;
+                }
+            }
+
+            if (mv != null && v != 0) {
+                int maxStack = readUnsignedShort(v);
+                int maxLocals = readUnsignedShort(v + 2);
+                int codeLength = readInt(v + 4);
+                v += 8;
+
+                int codeStart = v;
+                int codeEnd = v + codeLength;
+
+                mv.visitCode();
+
+                // 1st phase: finds the labels
+                int label;
+                Label[] labels = new Label[codeLength + 2];
+                readLabel(codeLength + 1, labels);
+                while (v < codeEnd) {
+                    w = v - codeStart;
+                    int opcode = b[v] & 0xFF;
+                    switch (ClassWriter.TYPE[opcode]) {
+                        case ClassWriter.NOARG_INSN:
+                        case ClassWriter.IMPLVAR_INSN:
+                            v += 1;
+                            break;
+                        case ClassWriter.LABEL_INSN:
+                            readLabel(w + readShort(v + 1), labels);
+                            v += 3;
+                            break;
+                        case ClassWriter.LABELW_INSN:
+                            readLabel(w + readInt(v + 1), labels);
+                            v += 5;
+                            break;
+                        case ClassWriter.WIDE_INSN:
+                            opcode = b[v + 1] & 0xFF;
+                            if (opcode == Opcodes.IINC) {
+                                v += 6;
+                            } else {
+                                v += 4;
+                            }
+                            break;
+                        case ClassWriter.TABL_INSN:
+                            // skips 0 to 3 padding bytes*
+                            v = v + 4 - (w & 3);
+                            // reads instruction
+                            readLabel(w + readInt(v), labels);
+                            j = readInt(v + 8) - readInt(v + 4) + 1;
+                            v += 12;
+                            for (; j > 0; --j) {
+                                readLabel(w + readInt(v), labels);
+                                v += 4;
+                            }
+                            break;
+                        case ClassWriter.LOOK_INSN:
+                            // skips 0 to 3 padding bytes*
+                            v = v + 4 - (w & 3);
+                            // reads instruction
+                            readLabel(w + readInt(v), labels);
+                            j = readInt(v + 4);
+                            v += 8;
+                            for (; j > 0; --j) {
+                                readLabel(w + readInt(v + 4), labels);
+                                v += 8;
+                            }
+                            break;
+                        case ClassWriter.VAR_INSN:
+                        case ClassWriter.SBYTE_INSN:
+                        case ClassWriter.LDC_INSN:
+                            v += 2;
+                            break;
+                        case ClassWriter.SHORT_INSN:
+                        case ClassWriter.LDCW_INSN:
+                        case ClassWriter.FIELDORMETH_INSN:
+                        case ClassWriter.TYPE_INSN:
+                        case ClassWriter.IINC_INSN:
+                            v += 3;
+                            break;
+                        case ClassWriter.ITFMETH_INSN:
+                        case ClassWriter.INDYMETH_INSN:
+                            v += 5;
+                            break;
+                        // case MANA_INSN:
+                        default:
+                            v += 4;
+                            break;
+                    }
+                }
+                // parses the try catch entries
+                j = readUnsignedShort(v);
+                v += 2;
+                for (; j > 0; --j) {
+                    Label start = readLabel(readUnsignedShort(v), labels);
+                    Label end = readLabel(readUnsignedShort(v + 2), labels);
+                    Label handler = readLabel(readUnsignedShort(v + 4), labels);
+                    int type = readUnsignedShort(v + 6);
+                    if (type == 0) {
+                        mv.visitTryCatchBlock(start, end, handler, null);
+                    } else {
+                        mv.visitTryCatchBlock(start,
+                                end,
+                                handler,
+                                readUTF8(items[type], c));
+                    }
+                    v += 8;
+                }
+                // parses the local variable, line number tables, and code
+                // attributes
+                int varTable = 0;
+                int varTypeTable = 0;
+                int stackMap = 0;
+                int stackMapSize = 0;
+                int frameCount = 0;
+                int frameMode = 0;
+                int frameOffset = 0;
+                int frameLocalCount = 0;
+                int frameLocalDiff = 0;
+                int frameStackCount = 0;
+                Object[] frameLocal = null;
+                Object[] frameStack = null;
+                boolean zip = true;
+                cattrs = null;
+                j = readUnsignedShort(v);
+                v += 2;
+                for (; j > 0; --j) {
+                    attrName = readUTF8(v, c);
+                    if ("LocalVariableTable".equals(attrName)) {
+                        if (!skipDebug) {
+                            varTable = v + 6;
+                            k = readUnsignedShort(v + 6);
+                            w = v + 8;
+                            for (; k > 0; --k) {
+                                label = readUnsignedShort(w);
+                                if (labels[label] == null) {
+                                    readLabel(label, labels).status |= Label.DEBUG;
+                                }
+                                label += readUnsignedShort(w + 2);
+                                if (labels[label] == null) {
+                                    readLabel(label, labels).status |= Label.DEBUG;
+                                }
+                                w += 10;
+                            }
+                        }
+                    } else if ("LocalVariableTypeTable".equals(attrName)) {
+                        varTypeTable = v + 6;
+                    } else if ("LineNumberTable".equals(attrName)) {
+                        if (!skipDebug) {
+                            k = readUnsignedShort(v + 6);
+                            w = v + 8;
+                            for (; k > 0; --k) {
+                                label = readUnsignedShort(w);
+                                if (labels[label] == null) {
+                                    readLabel(label, labels).status |= Label.DEBUG;
+                                }
+                                labels[label].line = readUnsignedShort(w + 2);
+                                w += 4;
+                            }
+                        }
+                    } else if (FRAMES && "StackMapTable".equals(attrName)) {
+                        if ((flags & SKIP_FRAMES) == 0) {
+                            stackMap = v + 8;
+                            stackMapSize = readInt(v + 2);
+                            frameCount = readUnsignedShort(v + 6);
+                        }
+                        /*
+                         * here we do not extract the labels corresponding to
+                         * the attribute content. This would require a full
+                         * parsing of the attribute, which would need to be
+                         * repeated in the second phase (see below). Instead the
+                         * content of the attribute is read one frame at a time
+                         * (i.e. after a frame has been visited, the next frame
+                         * is read), and the labels it contains are also
+                         * extracted one frame at a time. Thanks to the ordering
+                         * of frames, having only a "one frame lookahead" is not
+                         * a problem, i.e. it is not possible to see an offset
+                         * smaller than the offset of the current insn and for
+                         * which no Label exist.
+                         */
+                        /*
+                         * This is not true for UNINITIALIZED type offsets. We
+                         * solve this by parsing the stack map table without a
+                         * full decoding (see below).
+                         */
+                    } else if (FRAMES && "StackMap".equals(attrName)) {
+                        if ((flags & SKIP_FRAMES) == 0) {
+                            stackMap = v + 8;
+                            stackMapSize = readInt(v + 2);
+                            frameCount = readUnsignedShort(v + 6);
+                            zip = false;
+                        }
+                        /*
+                         * IMPORTANT! here we assume that the frames are
+                         * ordered, as in the StackMapTable attribute, although
+                         * this is not guaranteed by the attribute format.
+                         */
+                    } else {
+                        for (k = 0; k < attrs.length; ++k) {
+                            if (attrs[k].type.equals(attrName)) {
+                                attr = attrs[k].read(this,
+                                        v + 6,
+                                        readInt(v + 2),
+                                        c,
+                                        codeStart - 8,
+                                        labels);
+                                if (attr != null) {
+                                    attr.next = cattrs;
+                                    cattrs = attr;
+                                }
+                            }
+                        }
+                    }
+                    v += 6 + readInt(v + 2);
+                }
+
+                // 2nd phase: visits each instruction
+                if (FRAMES && stackMap != 0) {
+                    // creates the very first (implicit) frame from the method
+                    // descriptor
+                    frameLocal = new Object[maxLocals];
+                    frameStack = new Object[maxStack];
+                    if (unzip) {
+                        int local = 0;
+                        if ((access & Opcodes.ACC_STATIC) == 0) {
+                            if ("<init>".equals(name)) {
+                                frameLocal[local++] = Opcodes.UNINITIALIZED_THIS;
+                            } else {
+                                frameLocal[local++] = readClass(header + 2, c);
+                            }
+                        }
+                        j = 1;
+                        loop: while (true) {
+                            k = j;
+                            switch (desc.charAt(j++)) {
+                                case 'Z':
+                                case 'C':
+                                case 'B':
+                                case 'S':
+                                case 'I':
+                                    frameLocal[local++] = Opcodes.INTEGER;
+                                    break;
+                                case 'F':
+                                    frameLocal[local++] = Opcodes.FLOAT;
+                                    break;
+                                case 'J':
+                                    frameLocal[local++] = Opcodes.LONG;
+                                    break;
+                                case 'D':
+                                    frameLocal[local++] = Opcodes.DOUBLE;
+                                    break;
+                                case '[':
+                                    while (desc.charAt(j) == '[') {
+                                        ++j;
+                                    }
+                                    if (desc.charAt(j) == 'L') {
+                                        ++j;
+                                        while (desc.charAt(j) != ';') {
+                                            ++j;
+                                        }
+                                    }
+                                    frameLocal[local++] = desc.substring(k, ++j);
+                                    break;
+                                case 'L':
+                                    while (desc.charAt(j) != ';') {
+                                        ++j;
+                                    }
+                                    frameLocal[local++] = desc.substring(k + 1,
+                                            j++);
+                                    break;
+                                default:
+                                    break loop;
+                            }
+                        }
+                        frameLocalCount = local;
+                    }
+                    /*
+                     * for the first explicit frame the offset is not
+                     * offset_delta + 1 but only offset_delta; setting the
+                     * implicit frame offset to -1 allow the use of the
+                     * "offset_delta + 1" rule in all cases
+                     */
+                    frameOffset = -1;
+                    /*
+                     * Finds labels for UNINITIALIZED frame types. Instead of
+                     * decoding each element of the stack map table, we look
+                     * for 3 consecutive bytes that "look like" an UNINITIALIZED
+                     * type (tag 8, offset within code bounds, NEW instruction
+                     * at this offset). We may find false positives (i.e. not
+                     * real UNINITIALIZED types), but this should be rare, and
+                     * the only consequence will be the creation of an unneeded
+                     * label. This is better than creating a label for each NEW
+                     * instruction, and faster than fully decoding the whole
+                     * stack map table.
+                     */
+                    for (j = stackMap; j < stackMap + stackMapSize - 2; ++j) {
+                        if (b[j] == 8) { // UNINITIALIZED FRAME TYPE
+                            k = readUnsignedShort(j + 1);
+                            if (k >= 0 && k < codeLength) { // potential offset
+                                if ((b[codeStart + k] & 0xFF) == Opcodes.NEW) { // NEW at this offset
+                                    readLabel(k, labels);
+                                }
+                            }
+                        }
+                    }
+                }
+                v = codeStart;
+                Label l;
+                while (v < codeEnd) {
+                    w = v - codeStart;
+
+                    l = labels[w];
+                    if (l != null) {
+                        mv.visitLabel(l);
+                        if (!skipDebug && l.line > 0) {
+                            mv.visitLineNumber(l.line, l);
+                        }
+                    }
+
+                    while (FRAMES && frameLocal != null
+                            && (frameOffset == w || frameOffset == -1))
+                    {
+                        // if there is a frame for this offset,
+                        // makes the visitor visit it,
+                        // and reads the next frame if there is one.
+                        if (!zip || unzip) {
+                            mv.visitFrame(Opcodes.F_NEW,
+                                    frameLocalCount,
+                                    frameLocal,
+                                    frameStackCount,
+                                    frameStack);
+                        } else if (frameOffset != -1) {
+                            mv.visitFrame(frameMode,
+                                    frameLocalDiff,
+                                    frameLocal,
+                                    frameStackCount,
+                                    frameStack);
+                        }
+
+                        if (frameCount > 0) {
+                            int tag, delta, n;
+                            if (zip) {
+                                tag = b[stackMap++] & 0xFF;
+                            } else {
+                                tag = MethodWriter.FULL_FRAME;
+                                frameOffset = -1;
+                            }
+                            frameLocalDiff = 0;
+                            if (tag < MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME)
+                            {
+                                delta = tag;
+                                frameMode = Opcodes.F_SAME;
+                                frameStackCount = 0;
+                            } else if (tag < MethodWriter.RESERVED) {
+                                delta = tag
+                                        - MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME;
+                                stackMap = readFrameType(frameStack,
+                                        0,
+                                        stackMap,
+                                        c,
+                                        labels);
+                                frameMode = Opcodes.F_SAME1;
+                                frameStackCount = 1;
+                            } else {
+                                delta = readUnsignedShort(stackMap);
+                                stackMap += 2;
+                                if (tag == MethodWriter.SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED)
+                                {
+                                    stackMap = readFrameType(frameStack,
+                                            0,
+                                            stackMap,
+                                            c,
+                                            labels);
+                                    frameMode = Opcodes.F_SAME1;
+                                    frameStackCount = 1;
+                                } else if (tag >= MethodWriter.CHOP_FRAME
+                                        && tag < MethodWriter.SAME_FRAME_EXTENDED)
+                                {
+                                    frameMode = Opcodes.F_CHOP;
+                                    frameLocalDiff = MethodWriter.SAME_FRAME_EXTENDED
+                                            - tag;
+                                    frameLocalCount -= frameLocalDiff;
+                                    frameStackCount = 0;
+                                } else if (tag == MethodWriter.SAME_FRAME_EXTENDED)
+                                {
+                                    frameMode = Opcodes.F_SAME;
+                                    frameStackCount = 0;
+                                } else if (tag < MethodWriter.FULL_FRAME) {
+                                    j = unzip ? frameLocalCount : 0;
+                                    for (k = tag
+                                            - MethodWriter.SAME_FRAME_EXTENDED; k > 0; k--)
+                                    {
+                                        stackMap = readFrameType(frameLocal,
+                                                j++,
+                                                stackMap,
+                                                c,
+                                                labels);
+                                    }
+                                    frameMode = Opcodes.F_APPEND;
+                                    frameLocalDiff = tag
+                                            - MethodWriter.SAME_FRAME_EXTENDED;
+                                    frameLocalCount += frameLocalDiff;
+                                    frameStackCount = 0;
+                                } else { // if (tag == FULL_FRAME) {
+                                    frameMode = Opcodes.F_FULL;
+                                    n = frameLocalDiff = frameLocalCount = readUnsignedShort(stackMap);
+                                    stackMap += 2;
+                                    for (j = 0; n > 0; n--) {
+                                        stackMap = readFrameType(frameLocal,
+                                                j++,
+                                                stackMap,
+                                                c,
+                                                labels);
+                                    }
+                                    n = frameStackCount = readUnsignedShort(stackMap);
+                                    stackMap += 2;
+                                    for (j = 0; n > 0; n--) {
+                                        stackMap = readFrameType(frameStack,
+                                                j++,
+                                                stackMap,
+                                                c,
+                                                labels);
+                                    }
+                                }
+                            }
+                            frameOffset += delta + 1;
+                            readLabel(frameOffset, labels);
+
+                            --frameCount;
+                        } else {
+                            frameLocal = null;
+                        }
+                    }
+
+                    int opcode = b[v] & 0xFF;
+                    switch (ClassWriter.TYPE[opcode]) {
+                        case ClassWriter.NOARG_INSN:
+                            mv.visitInsn(opcode);
+                            v += 1;
+                            break;
+                        case ClassWriter.IMPLVAR_INSN:
+                            if (opcode > Opcodes.ISTORE) {
+                                opcode -= 59; // ISTORE_0
+                                mv.visitVarInsn(Opcodes.ISTORE + (opcode >> 2),
+                                        opcode & 0x3);
+                            } else {
+                                opcode -= 26; // ILOAD_0
+                                mv.visitVarInsn(Opcodes.ILOAD + (opcode >> 2),
+                                        opcode & 0x3);
+                            }
+                            v += 1;
+                            break;
+                        case ClassWriter.LABEL_INSN:
+                            mv.visitJumpInsn(opcode, labels[w
+                                    + readShort(v + 1)]);
+                            v += 3;
+                            break;
+                        case ClassWriter.LABELW_INSN:
+                            mv.visitJumpInsn(opcode - 33, labels[w
+                                    + readInt(v + 1)]);
+                            v += 5;
+                            break;
+                        case ClassWriter.WIDE_INSN:
+                            opcode = b[v + 1] & 0xFF;
+                            if (opcode == Opcodes.IINC) {
+                                mv.visitIincInsn(readUnsignedShort(v + 2),
+                                        readShort(v + 4));
+                                v += 6;
+                            } else {
+                                mv.visitVarInsn(opcode,
+                                        readUnsignedShort(v + 2));
+                                v += 4;
+                            }
+                            break;
+                        case ClassWriter.TABL_INSN:
+                            // skips 0 to 3 padding bytes
+                            v = v + 4 - (w & 3);
+                            // reads instruction
+                            label = w + readInt(v);
+                            int min = readInt(v + 4);
+                            int max = readInt(v + 8);
+                            v += 12;
+                            Label[] table = new Label[max - min + 1];
+                            for (j = 0; j < table.length; ++j) {
+                                table[j] = labels[w + readInt(v)];
+                                v += 4;
+                            }
+                            mv.visitTableSwitchInsn(min,
+                                    max,
+                                    labels[label],
+                                    table);
+                            break;
+                        case ClassWriter.LOOK_INSN:
+                            // skips 0 to 3 padding bytes
+                            v = v + 4 - (w & 3);
+                            // reads instruction
+                            label = w + readInt(v);
+                            j = readInt(v + 4);
+                            v += 8;
+                            int[] keys = new int[j];
+                            Label[] values = new Label[j];
+                            for (j = 0; j < keys.length; ++j) {
+                                keys[j] = readInt(v);
+                                values[j] = labels[w + readInt(v + 4)];
+                                v += 8;
+                            }
+                            mv.visitLookupSwitchInsn(labels[label],
+                                    keys,
+                                    values);
+                            break;
+                        case ClassWriter.VAR_INSN:
+                            mv.visitVarInsn(opcode, b[v + 1] & 0xFF);
+                            v += 2;
+                            break;
+                        case ClassWriter.SBYTE_INSN:
+                            mv.visitIntInsn(opcode, b[v + 1]);
+                            v += 2;
+                            break;
+                        case ClassWriter.SHORT_INSN:
+                            mv.visitIntInsn(opcode, readShort(v + 1));
+                            v += 3;
+                            break;
+                        case ClassWriter.LDC_INSN:
+                            mv.visitLdcInsn(readConst(b[v + 1] & 0xFF, c));
+                            v += 2;
+                            break;
+                        case ClassWriter.LDCW_INSN:
+                            mv.visitLdcInsn(readConst(readUnsignedShort(v + 1),
+                                    c));
+                            v += 3;
+                            break;
+                        case ClassWriter.FIELDORMETH_INSN:
+                        case ClassWriter.ITFMETH_INSN: {
+                            int cpIndex = items[readUnsignedShort(v + 1)];
+                            String iowner = readClass(cpIndex, c);
+                            cpIndex = items[readUnsignedShort(cpIndex + 2)];
+                            String iname = readUTF8(cpIndex, c);
+                            String idesc = readUTF8(cpIndex + 2, c);
+                            if (opcode < Opcodes.INVOKEVIRTUAL) {
+                                mv.visitFieldInsn(opcode, iowner, iname, idesc);
+                            } else {
+                                mv.visitMethodInsn(opcode, iowner, iname, idesc);
+                            }
+                            if (opcode == Opcodes.INVOKEINTERFACE) {
+                                v += 5;
+                            } else {
+                                v += 3;
+                            }
+                            break;
+                        }
+                        case ClassWriter.INDYMETH_INSN: {
+                            int cpIndex = items[readUnsignedShort(v + 1)];
+                            int bsmIndex = bootstrapMethods[readUnsignedShort(cpIndex)];
+                            cpIndex = items[readUnsignedShort(cpIndex + 2)];
+                            String iname = readUTF8(cpIndex, c);
+                            String idesc = readUTF8(cpIndex + 2, c);
+
+                            int mhIndex = readUnsignedShort(bsmIndex);
+                            Handle bsm = (Handle) readConst(mhIndex, c);
+                            int bsmArgCount = readUnsignedShort(bsmIndex + 2);
+                            Object[] bsmArgs = new Object[bsmArgCount];
+                            bsmIndex += 4;
+                            for(int a = 0; a < bsmArgCount; a++) {
+                                int argIndex = readUnsignedShort(bsmIndex);
+                                bsmArgs[a] = readConst(argIndex, c);
+                                bsmIndex += 2;
+                            }
+                            mv.visitInvokeDynamicInsn(iname, idesc, bsm, bsmArgs);
+
+                            v += 5;
+                            break;
+                        }
+                        case ClassWriter.TYPE_INSN:
+                            mv.visitTypeInsn(opcode, readClass(v + 1, c));
+                            v += 3;
+                            break;
+                        case ClassWriter.IINC_INSN:
+                            mv.visitIincInsn(b[v + 1] & 0xFF, b[v + 2]);
+                            v += 3;
+                            break;
+                        // case MANA_INSN:
+                        default:
+                            mv.visitMultiANewArrayInsn(readClass(v + 1, c),
+                                    b[v + 3] & 0xFF);
+                            v += 4;
+                            break;
+                    }
+                }
+                l = labels[codeEnd - codeStart];
+                if (l != null) {
+                    mv.visitLabel(l);
+                }
+                // visits the local variable tables
+                if (!skipDebug && varTable != 0) {
+                    int[] typeTable = null;
+                    if (varTypeTable != 0) {
+                        k = readUnsignedShort(varTypeTable) * 3;
+                        w = varTypeTable + 2;
+                        typeTable = new int[k];
+                        while (k > 0) {
+                            typeTable[--k] = w + 6; // signature
+                            typeTable[--k] = readUnsignedShort(w + 8); // index
+                            typeTable[--k] = readUnsignedShort(w); // start
+                            w += 10;
+                        }
+                    }
+                    k = readUnsignedShort(varTable);
+                    w = varTable + 2;
+                    for (; k > 0; --k) {
+                        int start = readUnsignedShort(w);
+                        int length = readUnsignedShort(w + 2);
+                        int index = readUnsignedShort(w + 8);
+                        String vsignature = null;
+                        if (typeTable != null) {
+                            for (int a = 0; a < typeTable.length; a += 3) {
+                                if (typeTable[a] == start
+                                        && typeTable[a + 1] == index)
+                                {
+                                    vsignature = readUTF8(typeTable[a + 2], c);
+                                    break;
+                                }
+                            }
+                        }
+                        mv.visitLocalVariable(readUTF8(w + 4, c),
+                                readUTF8(w + 6, c),
+                                vsignature,
+                                labels[start],
+                                labels[start + length],
+                                index);
+                        w += 10;
+                    }
+                }
+                // visits the other attributes
+                while (cattrs != null) {
+                    attr = cattrs.next;
+                    cattrs.next = null;
+                    mv.visitAttribute(cattrs);
+                    cattrs = attr;
+                }
+                // visits the max stack and max locals values
+                mv.visitMaxs(maxStack, maxLocals);
+            }
+
+            if (mv != null) {
+                mv.visitEnd();
+            }
+        }
+
+        // visits the end of the class
+        classVisitor.visitEnd();
+    }
+
+    /**
+     * Reads parameter annotations and makes the given visitor visit them.
+     *
+     * @param v start offset in {@link #b b} of the annotations to be read.
+     * @param desc the method descriptor.
+     * @param buf buffer to be used to call {@link #readUTF8 readUTF8},
+     *        {@link #readClass(int,char[]) readClass} or
+     *        {@link #readConst readConst}.
+     * @param visible <tt>true</tt> if the annotations to be read are visible
+     *        at runtime.
+     * @param mv the visitor that must visit the annotations.
+     */
+    private void readParameterAnnotations(
+        int v,
+        final String desc,
+        final char[] buf,
+        final boolean visible,
+        final MethodVisitor mv)
+    {
+        int i;
+        int n = b[v++] & 0xFF;
+        // workaround for a bug in javac (javac compiler generates a parameter
+        // annotation array whose size is equal to the number of parameters in
+        // the Java source file, while it should generate an array whose size is
+        // equal to the number of parameters in the method descriptor - which
+        // includes the synthetic parameters added by the compiler). This work-
+        // around supposes that the synthetic parameters are the first ones.
+        int synthetics = Type.getArgumentTypes(desc).length - n;
+        AnnotationVisitor av;
+        for (i = 0; i < synthetics; ++i) {
+            // virtual annotation to detect synthetic parameters in MethodWriter
+            av = mv.visitParameterAnnotation(i, "Ljava/lang/Synthetic;", false);
+            if (av != null) {
+                av.visitEnd();
+            }
+        }
+        for (; i < n + synthetics; ++i) {
+            int j = readUnsignedShort(v);
+            v += 2;
+            for (; j > 0; --j) {
+                av = mv.visitParameterAnnotation(i, readUTF8(v, buf), visible);
+                v = readAnnotationValues(v + 2, buf, true, av);
+            }
+        }
+    }
+
+    /**
+     * Reads the values of an annotation and makes the given visitor visit them.
+     *
+     * @param v the start offset in {@link #b b} of the values to be read
+     *        (including the unsigned short that gives the number of values).
+     * @param buf buffer to be used to call {@link #readUTF8 readUTF8},
+     *        {@link #readClass(int,char[]) readClass} or
+     *        {@link #readConst readConst}.
+     * @param named if the annotation values are named or not.
+     * @param av the visitor that must visit the values.
+     * @return the end offset of the annotation values.
+     */
+    private int readAnnotationValues(
+        int v,
+        final char[] buf,
+        final boolean named,
+        final AnnotationVisitor av)
+    {
+        int i = readUnsignedShort(v);
+        v += 2;
+        if (named) {
+            for (; i > 0; --i) {
+                v = readAnnotationValue(v + 2, buf, readUTF8(v, buf), av);
+            }
+        } else {
+            for (; i > 0; --i) {
+                v = readAnnotationValue(v, buf, null, av);
+            }
+        }
+        if (av != null) {
+            av.visitEnd();
+        }
+        return v;
+    }
+
+    /**
+     * Reads a value of an annotation and makes the given visitor visit it.
+     *
+     * @param v the start offset in {@link #b b} of the value to be read (<i>not
+     *        including the value name constant pool index</i>).
+     * @param buf buffer to be used to call {@link #readUTF8 readUTF8},
+     *        {@link #readClass(int,char[]) readClass} or
+     *        {@link #readConst readConst}.
+     * @param name the name of the value to be read.
+     * @param av the visitor that must visit the value.
+     * @return the end offset of the annotation value.
+     */
+    private int readAnnotationValue(
+        int v,
+        final char[] buf,
+        final String name,
+        final AnnotationVisitor av)
+    {
+        int i;
+        if (av == null) {
+            switch (b[v] & 0xFF) {
+                case 'e': // enum_const_value
+                    return v + 5;
+                case '@': // annotation_value
+                    return readAnnotationValues(v + 3, buf, true, null);
+                case '[': // array_value
+                    return readAnnotationValues(v + 1, buf, false, null);
+                default:
+                    return v + 3;
+            }
+        }
+        switch (b[v++] & 0xFF) {
+            case 'I': // pointer to CONSTANT_Integer
+            case 'J': // pointer to CONSTANT_Long
+            case 'F': // pointer to CONSTANT_Float
+            case 'D': // pointer to CONSTANT_Double
+                av.visit(name, readConst(readUnsignedShort(v), buf));
+                v += 2;
+                break;
+            case 'B': // pointer to CONSTANT_Byte
+                av.visit(name,
+                        new Byte((byte) readInt(items[readUnsignedShort(v)])));
+                v += 2;
+                break;
+            case 'Z': // pointer to CONSTANT_Boolean
+                av.visit(name, readInt(items[readUnsignedShort(v)]) == 0
+                        ? Boolean.FALSE
+                        : Boolean.TRUE);
+                v += 2;
+                break;
+            case 'S': // pointer to CONSTANT_Short
+                av.visit(name,
+                        new Short((short) readInt(items[readUnsignedShort(v)])));
+                v += 2;
+                break;
+            case 'C': // pointer to CONSTANT_Char
+                av.visit(name,
+                        new Character((char) readInt(items[readUnsignedShort(v)])));
+                v += 2;
+                break;
+            case 's': // pointer to CONSTANT_Utf8
+                av.visit(name, readUTF8(v, buf));
+                v += 2;
+                break;
+            case 'e': // enum_const_value
+                av.visitEnum(name, readUTF8(v, buf), readUTF8(v + 2, buf));
+                v += 4;
+                break;
+            case 'c': // class_info
+                av.visit(name, Type.getType(readUTF8(v, buf)));
+                v += 2;
+                break;
+            case '@': // annotation_value
+                v = readAnnotationValues(v + 2,
+                        buf,
+                        true,
+                        av.visitAnnotation(name, readUTF8(v, buf)));
+                break;
+            case '[': // array_value
+                int size = readUnsignedShort(v);
+                v += 2;
+                if (size == 0) {
+                    return readAnnotationValues(v - 2,
+                            buf,
+                            false,
+                            av.visitArray(name));
+                }
+                switch (this.b[v++] & 0xFF) {
+                    case 'B':
+                        byte[] bv = new byte[size];
+                        for (i = 0; i < size; i++) {
+                            bv[i] = (byte) readInt(items[readUnsignedShort(v)]);
+                            v += 3;
+                        }
+                        av.visit(name, bv);
+                        --v;
+                        break;
+                    case 'Z':
+                        boolean[] zv = new boolean[size];
+                        for (i = 0; i < size; i++) {
+                            zv[i] = readInt(items[readUnsignedShort(v)]) != 0;
+                            v += 3;
+                        }
+                        av.visit(name, zv);
+                        --v;
+                        break;
+                    case 'S':
+                        short[] sv = new short[size];
+                        for (i = 0; i < size; i++) {
+                            sv[i] = (short) readInt(items[readUnsignedShort(v)]);
+                            v += 3;
+                        }
+                        av.visit(name, sv);
+                        --v;
+                        break;
+                    case 'C':
+                        char[] cv = new char[size];
+                        for (i = 0; i < size; i++) {
+                            cv[i] = (char) readInt(items[readUnsignedShort(v)]);
+                            v += 3;
+                        }
+                        av.visit(name, cv);
+                        --v;
+                        break;
+                    case 'I':
+                        int[] iv = new int[size];
+                        for (i = 0; i < size; i++) {
+                            iv[i] = readInt(items[readUnsignedShort(v)]);
+                            v += 3;
+                        }
+                        av.visit(name, iv);
+                        --v;
+                        break;
+                    case 'J':
+                        long[] lv = new long[size];
+                        for (i = 0; i < size; i++) {
+                            lv[i] = readLong(items[readUnsignedShort(v)]);
+                            v += 3;
+                        }
+                        av.visit(name, lv);
+                        --v;
+                        break;
+                    case 'F':
+                        float[] fv = new float[size];
+                        for (i = 0; i < size; i++) {
+                            fv[i] = Float.intBitsToFloat(readInt(items[readUnsignedShort(v)]));
+                            v += 3;
+                        }
+                        av.visit(name, fv);
+                        --v;
+                        break;
+                    case 'D':
+                        double[] dv = new double[size];
+                        for (i = 0; i < size; i++) {
+                            dv[i] = Double.longBitsToDouble(readLong(items[readUnsignedShort(v)]));
+                            v += 3;
+                        }
+                        av.visit(name, dv);
+                        --v;
+                        break;
+                    default:
+                        v = readAnnotationValues(v - 3,
+                                buf,
+                                false,
+                                av.visitArray(name));
+                }
+        }
+        return v;
+    }
+
+    private int readFrameType(
+        final Object[] frame,
+        final int index,
+        int v,
+        final char[] buf,
+        final Label[] labels)
+    {
+        int type = b[v++] & 0xFF;
+        switch (type) {
+            case 0:
+                frame[index] = Opcodes.TOP;
+                break;
+            case 1:
+                frame[index] = Opcodes.INTEGER;
+                break;
+            case 2:
+                frame[index] = Opcodes.FLOAT;
+                break;
+            case 3:
+                frame[index] = Opcodes.DOUBLE;
+                break;
+            case 4:
+                frame[index] = Opcodes.LONG;
+                break;
+            case 5:
+                frame[index] = Opcodes.NULL;
+                break;
+            case 6:
+                frame[index] = Opcodes.UNINITIALIZED_THIS;
+                break;
+            case 7: // Object
+                frame[index] = readClass(v, buf);
+                v += 2;
+                break;
+            default: // Uninitialized
+                frame[index] = readLabel(readUnsignedShort(v), labels);
+                v += 2;
+        }
+        return v;
+    }
+
+    /**
+     * Returns the label corresponding to the given offset. The default
+     * implementation of this method creates a label for the given offset if it
+     * has not been already created.
+     *
+     * @param offset a bytecode offset in a method.
+     * @param labels the already created labels, indexed by their offset. If a
+     *        label already exists for offset this method must not create a new
+     *        one. Otherwise it must store the new label in this array.
+     * @return a non null Label, which must be equal to labels[offset].
+     */
+    protected Label readLabel(int offset, Label[] labels) {
+        if (labels[offset] == null) {
+            labels[offset] = new Label();
+        }
+        return labels[offset];
+    }
+
+    /**
+     * Reads an attribute in {@link #b b}.
+     *
+     * @param attrs prototypes of the attributes that must be parsed during the
+     *        visit of the class. Any attribute whose type is not equal to the
+     *        type of one the prototypes is ignored (i.e. an empty
+     *        {@link Attribute} instance is returned).
+     * @param type the type of the attribute.
+     * @param off index of the first byte of the attribute's content in
+     *        {@link #b b}. The 6 attribute header bytes, containing the type
+     *        and the length of the attribute, are not taken into account here
+     *        (they have already been read).
+     * @param len the length of the attribute's content.
+     * @param buf buffer to be used to call {@link #readUTF8 readUTF8},
+     *        {@link #readClass(int,char[]) readClass} or
+     *        {@link #readConst readConst}.
+     * @param codeOff index of the first byte of code's attribute content in
+     *        {@link #b b}, or -1 if the attribute to be read is not a code
+     *        attribute. The 6 attribute header bytes, containing the type and
+     *        the length of the attribute, are not taken into account here.
+     * @param labels the labels of the method's code, or <tt>null</tt> if the
+     *        attribute to be read is not a code attribute.
+     * @return the attribute that has been read, or <tt>null</tt> to skip this
+     *         attribute.
+     */
+    private Attribute readAttribute(
+        final Attribute[] attrs,
+        final String type,
+        final int off,
+        final int len,
+        final char[] buf,
+        final int codeOff,
+        final Label[] labels)
+    {
+        for (int i = 0; i < attrs.length; ++i) {
+            if (attrs[i].type.equals(type)) {
+                return attrs[i].read(this, off, len, buf, codeOff, labels);
+            }
+        }
+        return new Attribute(type).read(this, off, len, null, -1, null);
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods: low level parsing
+    // ------------------------------------------------------------------------
+
+    /**
+     *  Returns the number of constant pool items in {@link #b b}.
+     *
+     *  @return the number of constant pool items in {@link #b b}.
+     */
+    public int getItemCount() {
+        return items.length;
+    }
+
+    /**
+     * Returns the start index of the constant pool item in {@link #b b}, plus
+     * one. <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param item the index a constant pool item.
+     * @return the start index of the constant pool item in {@link #b b}, plus
+     *         one.
+     */
+    public int getItem(final int item) {
+        return items[item];
+    }
+
+    /**
+     * Returns the maximum length of the strings contained in the constant pool
+     * of the class.
+     *
+     * @return the maximum length of the strings contained in the constant pool
+     *         of the class.
+     */
+    public int getMaxStringLength() {
+        return maxStringLength;
+    }
+
+    /**
+     * Reads a byte value in {@link #b b}. <i>This method is intended for
+     * {@link Attribute} sub classes, and is normally not needed by class
+     * generators or adapters.</i>
+     *
+     * @param index the start index of the value to be read in {@link #b b}.
+     * @return the read value.
+     */
+    public int readByte(final int index) {
+        return b[index] & 0xFF;
+    }
+
+    /**
+     * Reads an unsigned short value in {@link #b b}. <i>This method is
+     * intended for {@link Attribute} sub classes, and is normally not needed by
+     * class generators or adapters.</i>
+     *
+     * @param index the start index of the value to be read in {@link #b b}.
+     * @return the read value.
+     */
+    public int readUnsignedShort(final int index) {
+        byte[] b = this.b;
+        return ((b[index] & 0xFF) << 8) | (b[index + 1] & 0xFF);
+    }
+
+    /**
+     * Reads a signed short value in {@link #b b}. <i>This method is intended
+     * for {@link Attribute} sub classes, and is normally not needed by class
+     * generators or adapters.</i>
+     *
+     * @param index the start index of the value to be read in {@link #b b}.
+     * @return the read value.
+     */
+    public short readShort(final int index) {
+        byte[] b = this.b;
+        return (short) (((b[index] & 0xFF) << 8) | (b[index + 1] & 0xFF));
+    }
+
+    /**
+     * Reads a signed int value in {@link #b b}. <i>This method is intended for
+     * {@link Attribute} sub classes, and is normally not needed by class
+     * generators or adapters.</i>
+     *
+     * @param index the start index of the value to be read in {@link #b b}.
+     * @return the read value.
+     */
+    public int readInt(final int index) {
+        byte[] b = this.b;
+        return ((b[index] & 0xFF) << 24) | ((b[index + 1] & 0xFF) << 16)
+                | ((b[index + 2] & 0xFF) << 8) | (b[index + 3] & 0xFF);
+    }
+
+    /**
+     * Reads a signed long value in {@link #b b}. <i>This method is intended
+     * for {@link Attribute} sub classes, and is normally not needed by class
+     * generators or adapters.</i>
+     *
+     * @param index the start index of the value to be read in {@link #b b}.
+     * @return the read value.
+     */
+    public long readLong(final int index) {
+        long l1 = readInt(index);
+        long l0 = readInt(index + 4) & 0xFFFFFFFFL;
+        return (l1 << 32) | l0;
+    }
+
+    /**
+     * Reads an UTF8 string constant pool item in {@link #b b}. <i>This method
+     * is intended for {@link Attribute} sub classes, and is normally not needed
+     * by class generators or adapters.</i>
+     *
+     * @param index the start index of an unsigned short value in {@link #b b},
+     *        whose value is the index of an UTF8 constant pool item.
+     * @param buf buffer to be used to read the item. This buffer must be
+     *        sufficiently large. It is not automatically resized.
+     * @return the String corresponding to the specified UTF8 item.
+     */
+    public String readUTF8(int index, final char[] buf) {
+        int item = readUnsignedShort(index);
+        String s = strings[item];
+        if (s != null) {
+            return s;
+        }
+        index = items[item];
+        return strings[item] = readUTF(index + 2, readUnsignedShort(index), buf);
+    }
+
+    /**
+     * Reads UTF8 string in {@link #b b}.
+     *
+     * @param index start offset of the UTF8 string to be read.
+     * @param utfLen length of the UTF8 string to be read.
+     * @param buf buffer to be used to read the string. This buffer must be
+     *        sufficiently large. It is not automatically resized.
+     * @return the String corresponding to the specified UTF8 string.
+     */
+    private String readUTF(int index, final int utfLen, final char[] buf) {
+        int endIndex = index + utfLen;
+        byte[] b = this.b;
+        int strLen = 0;
+        int c;
+        int st = 0;
+        char cc = 0;
+        while (index < endIndex) {
+            c = b[index++];
+            switch (st) {
+                case 0:
+                    c = c & 0xFF;
+                    if (c < 0x80) {  // 0xxxxxxx
+                        buf[strLen++] = (char) c;
+                    } else if (c < 0xE0 && c > 0xBF) {  // 110x xxxx 10xx xxxx
+                        cc = (char) (c & 0x1F);
+                        st = 1;
+                    } else {  // 1110 xxxx 10xx xxxx 10xx xxxx
+                        cc = (char) (c & 0x0F);
+                        st = 2;
+                    }
+                    break;
+
+                case 1:  // byte 2 of 2-byte char or byte 3 of 3-byte char
+                    buf[strLen++] = (char) ((cc << 6) | (c & 0x3F));
+                    st = 0;
+                    break;
+
+                case 2:  // byte 2 of 3-byte char
+                    cc = (char) ((cc << 6) | (c & 0x3F));
+                    st = 1;
+                    break;
+            }
+        }
+        return new String(buf, 0, strLen);
+    }
+
+    /**
+     * Reads a class constant pool item in {@link #b b}. <i>This method is
+     * intended for {@link Attribute} sub classes, and is normally not needed by
+     * class generators or adapters.</i>
+     *
+     * @param index the start index of an unsigned short value in {@link #b b},
+     *        whose value is the index of a class constant pool item.
+     * @param buf buffer to be used to read the item. This buffer must be
+     *        sufficiently large. It is not automatically resized.
+     * @return the String corresponding to the specified class item.
+     */
+    public String readClass(final int index, final char[] buf) {
+        // computes the start index of the CONSTANT_Class item in b
+        // and reads the CONSTANT_Utf8 item designated by
+        // the first two bytes of this CONSTANT_Class item
+        return readUTF8(items[readUnsignedShort(index)], buf);
+    }
+
+    /**
+     * Reads a numeric or string constant pool item in {@link #b b}. <i>This
+     * method is intended for {@link Attribute} sub classes, and is normally not
+     * needed by class generators or adapters.</i>
+     *
+     * @param item the index of a constant pool item.
+     * @param buf buffer to be used to read the item. This buffer must be
+     *        sufficiently large. It is not automatically resized.
+     * @return the {@link Integer}, {@link Float}, {@link Long}, {@link Double},
+     *         {@link String}, {@link Type} or {@link Handle} corresponding to
+     *         the given constant pool item.
+     */
+    public Object readConst(final int item, final char[] buf) {
+        int index = items[item];
+        switch (b[index - 1]) {
+            case ClassWriter.INT:
+                return new Integer(readInt(index));
+            case ClassWriter.FLOAT:
+                return new Float(Float.intBitsToFloat(readInt(index)));
+            case ClassWriter.LONG:
+                return new Long(readLong(index));
+            case ClassWriter.DOUBLE:
+                return new Double(Double.longBitsToDouble(readLong(index)));
+            case ClassWriter.CLASS:
+                return Type.getObjectType(readUTF8(index, buf));
+            case ClassWriter.STR:
+                return readUTF8(index, buf);
+            case ClassWriter.MTYPE:
+                return Type.getMethodType(readUTF8(index, buf));
+
+            //case ClassWriter.HANDLE_BASE + [1..9]:
+            default: {
+                int tag = readByte(index);
+                int[] items = this.items;
+                int cpIndex = items[readUnsignedShort(index + 1)];
+                String owner = readClass(cpIndex, buf);
+                cpIndex = items[readUnsignedShort(cpIndex + 2)];
+                String name = readUTF8(cpIndex, buf);
+                String desc = readUTF8(cpIndex + 2, buf);
+                return new Handle(tag, owner, name, desc);
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/ClassVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,306 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A visitor to visit a Java class. The methods of this class must be called
+ * in the following order: <tt>visit</tt> [ <tt>visitSource</tt> ] [
+ * <tt>visitOuterClass</tt> ] ( <tt>visitAnnotation</tt> |
+ * <tt>visitAttribute</tt> )* ( <tt>visitInnerClass</tt> |
+ * <tt>visitField</tt> | <tt>visitMethod</tt> )* <tt>visitEnd</tt>.
+ *
+ * @author Eric Bruneton
+ */
+public abstract class ClassVisitor {
+
+    /**
+     * The ASM API version implemented by this visitor. The value of this field
+     * must be one of {@link Opcodes#ASM4}.
+     */
+    protected final int api;
+
+    /**
+     * The class visitor to which this visitor must delegate method calls. May
+     * be null.
+     */
+    protected ClassVisitor cv;
+
+    /**
+     * Constructs a new {@link ClassVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public ClassVisitor(final int api) {
+        this(api, null);
+    }
+
+    /**
+     * Constructs a new {@link ClassVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param cv the class visitor to which this visitor must delegate method
+     *        calls. May be null.
+     */
+    public ClassVisitor(final int api, final ClassVisitor cv) {
+        /*if (api != Opcodes.ASM4) {
+            throw new IllegalArgumentException();
+        }*/
+        this.api = api;
+        this.cv = cv;
+    }
+
+    /**
+     * Visits the header of the class.
+     *
+     * @param version the class version.
+     * @param access the class's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the class is deprecated.
+     * @param name the internal name of the class (see
+     *        {@link Type#getInternalName() getInternalName}).
+     * @param signature the signature of this class. May be <tt>null</tt> if
+     *        the class is not a generic one, and does not extend or implement
+     *        generic classes or interfaces.
+     * @param superName the internal of name of the super class (see
+     *        {@link Type#getInternalName() getInternalName}). For interfaces,
+     *        the super class is {@link Object}. May be <tt>null</tt>, but
+     *        only for the {@link Object} class.
+     * @param interfaces the internal names of the class's interfaces (see
+     *        {@link Type#getInternalName() getInternalName}). May be
+     *        <tt>null</tt>.
+     */
+    public void visit(
+        int version,
+        int access,
+        String name,
+        String signature,
+        String superName,
+        String[] interfaces)
+    {
+        if (cv != null) {
+            cv.visit(version, access, name, signature, superName, interfaces);
+        }
+    }
+
+    /**
+     * Visits the source of the class.
+     *
+     * @param source the name of the source file from which the class was
+     *        compiled. May be <tt>null</tt>.
+     * @param debug additional debug information to compute the correspondance
+     *        between source and compiled elements of the class. May be
+     *        <tt>null</tt>.
+     */
+    public void visitSource(String source, String debug) {
+        if (cv != null) {
+            cv.visitSource(source, debug);
+        }
+    }
+
+    /**
+     * Visits the enclosing class of the class. This method must be called only
+     * if the class has an enclosing class.
+     *
+     * @param owner internal name of the enclosing class of the class.
+     * @param name the name of the method that contains the class, or
+     *        <tt>null</tt> if the class is not enclosed in a method of its
+     *        enclosing class.
+     * @param desc the descriptor of the method that contains the class, or
+     *        <tt>null</tt> if the class is not enclosed in a method of its
+     *        enclosing class.
+     */
+    public void visitOuterClass(String owner, String name, String desc) {
+        if (cv != null)  {
+            cv.visitOuterClass(owner, name, desc);
+        }
+    }
+
+    /**
+     * Visits an annotation of the class.
+     *
+     * @param desc the class descriptor of the annotation class.
+     * @param visible <tt>true</tt> if the annotation is visible at runtime.
+     * @return a visitor to visit the annotation values, or <tt>null</tt> if
+     *         this visitor is not interested in visiting this annotation.
+     */
+    public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
+        if (cv != null) {
+            return cv.visitAnnotation(desc, visible);
+        }
+        return null;
+    }
+
+    /**
+     * Visits a non standard attribute of the class.
+     *
+     * @param attr an attribute.
+     */
+    public void visitAttribute(Attribute attr) {
+        if (cv != null) {
+            cv.visitAttribute(attr);
+        }
+    }
+
+    /**
+     * Visits information about an inner class. This inner class is not
+     * necessarily a member of the class being visited.
+     *
+     * @param name the internal name of an inner class (see
+     *        {@link Type#getInternalName() getInternalName}).
+     * @param outerName the internal name of the class to which the inner class
+     *        belongs (see {@link Type#getInternalName() getInternalName}). May
+     *        be <tt>null</tt> for not member classes.
+     * @param innerName the (simple) name of the inner class inside its
+     *        enclosing class. May be <tt>null</tt> for anonymous inner
+     *        classes.
+     * @param access the access flags of the inner class as originally declared
+     *        in the enclosing class.
+     */
+    public void visitInnerClass(
+        String name,
+        String outerName,
+        String innerName,
+        int access)
+    {
+        if (cv != null) {
+            cv.visitInnerClass(name, outerName, innerName, access);
+        }
+    }
+
+    /**
+     * Visits a field of the class.
+     *
+     * @param access the field's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the field is synthetic and/or
+     *        deprecated.
+     * @param name the field's name.
+     * @param desc the field's descriptor (see {@link Type Type}).
+     * @param signature the field's signature. May be <tt>null</tt> if the
+     *        field's type does not use generic types.
+     * @param value the field's initial value. This parameter, which may be
+     *        <tt>null</tt> if the field does not have an initial value, must
+     *        be an {@link Integer}, a {@link Float}, a {@link Long}, a
+     *        {@link Double} or a {@link String} (for <tt>int</tt>,
+     *        <tt>float</tt>, <tt>long</tt> or <tt>String</tt> fields
+     *        respectively). <i>This parameter is only used for static fields</i>.
+     *        Its value is ignored for non static fields, which must be
+     *        initialized through bytecode instructions in constructors or
+     *        methods.
+     * @return a visitor to visit field annotations and attributes, or
+     *         <tt>null</tt> if this class visitor is not interested in
+     *         visiting these annotations and attributes.
+     */
+    public FieldVisitor visitField(
+        int access,
+        String name,
+        String desc,
+        String signature,
+        Object value)
+    {
+        if (cv != null) {
+            return cv.visitField(access, name, desc, signature, value);
+        }
+        return null;
+    }
+
+    /**
+     * Visits a method of the class. This method <i>must</i> return a new
+     * {@link MethodVisitor} instance (or <tt>null</tt>) each time it is
+     * called, i.e., it should not return a previously returned visitor.
+     *
+     * @param access the method's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the method is synthetic and/or
+     *        deprecated.
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param signature the method's signature. May be <tt>null</tt> if the
+     *        method parameters, return type and exceptions do not use generic
+     *        types.
+     * @param exceptions the internal names of the method's exception classes
+     *        (see {@link Type#getInternalName() getInternalName}). May be
+     *        <tt>null</tt>.
+     * @return an object to visit the byte code of the method, or <tt>null</tt>
+     *         if this class visitor is not interested in visiting the code of
+     *         this method.
+     */
+    public MethodVisitor visitMethod(
+        int access,
+        String name,
+        String desc,
+        String signature,
+        String[] exceptions)
+    {
+        if (cv != null) {
+            return cv.visitMethod(access, name, desc, signature, exceptions);
+        }
+        return null;
+    }
+
+    /**
+     * Visits the end of the class. This method, which is the last one to be
+     * called, is used to inform the visitor that all the fields and methods of
+     * the class have been visited.
+     */
+    public void visitEnd() {
+        if (cv != null) {
+            cv.visitEnd();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/ClassWriter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1701 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A {@link ClassVisitor} that generates classes in bytecode form. More
+ * precisely this visitor generates a byte array conforming to the Java class
+ * file format. It can be used alone, to generate a Java class "from scratch",
+ * or with one or more {@link ClassReader ClassReader} and adapter class visitor
+ * to generate a modified class from one or more existing Java classes.
+ *
+ * @author Eric Bruneton
+ */
+public class ClassWriter extends ClassVisitor {
+
+    /**
+     * Flag to automatically compute the maximum stack size and the maximum
+     * number of local variables of methods. If this flag is set, then the
+     * arguments of the {@link MethodVisitor#visitMaxs visitMaxs} method of the
+     * {@link MethodVisitor} returned by the {@link #visitMethod visitMethod}
+     * method will be ignored, and computed automatically from the signature and
+     * the bytecode of each method.
+     *
+     * @see #ClassWriter(int)
+     */
+    public static final int COMPUTE_MAXS = 1;
+
+    /**
+     * Flag to automatically compute the stack map frames of methods from
+     * scratch. If this flag is set, then the calls to the
+     * {@link MethodVisitor#visitFrame} method are ignored, and the stack map
+     * frames are recomputed from the methods bytecode. The arguments of the
+     * {@link MethodVisitor#visitMaxs visitMaxs} method are also ignored and
+     * recomputed from the bytecode. In other words, computeFrames implies
+     * computeMaxs.
+     *
+     * @see #ClassWriter(int)
+     */
+    public static final int COMPUTE_FRAMES = 2;
+
+    /**
+     * Pseudo access flag to distinguish between the synthetic attribute and
+     * the synthetic access flag.
+     */
+    static final int ACC_SYNTHETIC_ATTRIBUTE = 0x40000;
+
+    /**
+     * The type of instructions without any argument.
+     */
+    static final int NOARG_INSN = 0;
+
+    /**
+     * The type of instructions with an signed byte argument.
+     */
+    static final int SBYTE_INSN = 1;
+
+    /**
+     * The type of instructions with an signed short argument.
+     */
+    static final int SHORT_INSN = 2;
+
+    /**
+     * The type of instructions with a local variable index argument.
+     */
+    static final int VAR_INSN = 3;
+
+    /**
+     * The type of instructions with an implicit local variable index argument.
+     */
+    static final int IMPLVAR_INSN = 4;
+
+    /**
+     * The type of instructions with a type descriptor argument.
+     */
+    static final int TYPE_INSN = 5;
+
+    /**
+     * The type of field and method invocations instructions.
+     */
+    static final int FIELDORMETH_INSN = 6;
+
+    /**
+     * The type of the INVOKEINTERFACE/INVOKEDYNAMIC instruction.
+     */
+    static final int ITFMETH_INSN = 7;
+
+    /**
+     * The type of the INVOKEDYNAMIC instruction.
+     */
+    static final int INDYMETH_INSN = 8;
+
+    /**
+     * The type of instructions with a 2 bytes bytecode offset label.
+     */
+    static final int LABEL_INSN = 9;
+
+    /**
+     * The type of instructions with a 4 bytes bytecode offset label.
+     */
+    static final int LABELW_INSN = 10;
+
+    /**
+     * The type of the LDC instruction.
+     */
+    static final int LDC_INSN = 11;
+
+    /**
+     * The type of the LDC_W and LDC2_W instructions.
+     */
+    static final int LDCW_INSN = 12;
+
+    /**
+     * The type of the IINC instruction.
+     */
+    static final int IINC_INSN = 13;
+
+    /**
+     * The type of the TABLESWITCH instruction.
+     */
+    static final int TABL_INSN = 14;
+
+    /**
+     * The type of the LOOKUPSWITCH instruction.
+     */
+    static final int LOOK_INSN = 15;
+
+    /**
+     * The type of the MULTIANEWARRAY instruction.
+     */
+    static final int MANA_INSN = 16;
+
+    /**
+     * The type of the WIDE instruction.
+     */
+    static final int WIDE_INSN = 17;
+
+    /**
+     * The instruction types of all JVM opcodes.
+     */
+    static final byte[] TYPE;
+
+    /**
+     * The type of CONSTANT_Class constant pool items.
+     */
+    static final int CLASS = 7;
+
+    /**
+     * The type of CONSTANT_Fieldref constant pool items.
+     */
+    static final int FIELD = 9;
+
+    /**
+     * The type of CONSTANT_Methodref constant pool items.
+     */
+    static final int METH = 10;
+
+    /**
+     * The type of CONSTANT_InterfaceMethodref constant pool items.
+     */
+    static final int IMETH = 11;
+
+    /**
+     * The type of CONSTANT_String constant pool items.
+     */
+    static final int STR = 8;
+
+    /**
+     * The type of CONSTANT_Integer constant pool items.
+     */
+    static final int INT = 3;
+
+    /**
+     * The type of CONSTANT_Float constant pool items.
+     */
+    static final int FLOAT = 4;
+
+    /**
+     * The type of CONSTANT_Long constant pool items.
+     */
+    static final int LONG = 5;
+
+    /**
+     * The type of CONSTANT_Double constant pool items.
+     */
+    static final int DOUBLE = 6;
+
+    /**
+     * The type of CONSTANT_NameAndType constant pool items.
+     */
+    static final int NAME_TYPE = 12;
+
+    /**
+     * The type of CONSTANT_Utf8 constant pool items.
+     */
+    static final int UTF8 = 1;
+
+    /**
+     * The type of CONSTANT_MethodType constant pool items.
+     */
+    static final int MTYPE = 16;
+
+    /**
+     * The type of CONSTANT_MethodHandle constant pool items.
+     */
+    static final int HANDLE = 15;
+
+    /**
+     * The type of CONSTANT_InvokeDynamic constant pool items.
+     */
+    static final int INDY = 18;
+
+    /**
+     * The base value for all CONSTANT_MethodHandle constant pool items.
+     * Internally, ASM store the 9 variations of CONSTANT_MethodHandle into
+     * 9 different items.
+     */
+    static final int HANDLE_BASE = 20;
+
+    /**
+     * Normal type Item stored in the ClassWriter {@link ClassWriter#typeTable},
+     * instead of the constant pool, in order to avoid clashes with normal
+     * constant pool items in the ClassWriter constant pool's hash table.
+     */
+    static final int TYPE_NORMAL = 30;
+
+    /**
+     * Uninitialized type Item stored in the ClassWriter
+     * {@link ClassWriter#typeTable}, instead of the constant pool, in order to
+     * avoid clashes with normal constant pool items in the ClassWriter constant
+     * pool's hash table.
+     */
+    static final int TYPE_UNINIT = 31;
+
+    /**
+     * Merged type Item stored in the ClassWriter {@link ClassWriter#typeTable},
+     * instead of the constant pool, in order to avoid clashes with normal
+     * constant pool items in the ClassWriter constant pool's hash table.
+     */
+    static final int TYPE_MERGED = 32;
+
+    /**
+     * The type of BootstrapMethods items. These items are stored in a
+     * special class attribute named BootstrapMethods and
+     * not in the constant pool.
+     */
+    static final int BSM = 33;
+
+    /**
+     * The class reader from which this class writer was constructed, if any.
+     */
+    ClassReader cr;
+
+    /**
+     * Minor and major version numbers of the class to be generated.
+     */
+    int version;
+
+    /**
+     * Index of the next item to be added in the constant pool.
+     */
+    int index;
+
+    /**
+     * The constant pool of this class.
+     */
+    final ByteVector pool;
+
+    /**
+     * The constant pool's hash table data.
+     */
+    Item[] items;
+
+    /**
+     * The threshold of the constant pool's hash table.
+     */
+    int threshold;
+
+    /**
+     * A reusable key used to look for items in the {@link #items} hash table.
+     */
+    final Item key;
+
+    /**
+     * A reusable key used to look for items in the {@link #items} hash table.
+     */
+    final Item key2;
+
+    /**
+     * A reusable key used to look for items in the {@link #items} hash table.
+     */
+    final Item key3;
+
+    /**
+     * A reusable key used to look for items in the {@link #items} hash table.
+     */
+    final Item key4;
+
+    /**
+     * A type table used to temporarily store internal names that will not
+     * necessarily be stored in the constant pool. This type table is used by
+     * the control flow and data flow analysis algorithm used to compute stack
+     * map frames from scratch. This array associates to each index <tt>i</tt>
+     * the Item whose index is <tt>i</tt>. All Item objects stored in this
+     * array are also stored in the {@link #items} hash table. These two arrays
+     * allow to retrieve an Item from its index or, conversely, to get the index
+     * of an Item from its value. Each Item stores an internal name in its
+     * {@link Item#strVal1} field.
+     */
+    Item[] typeTable;
+
+    /**
+     * Number of elements in the {@link #typeTable} array.
+     */
+    private short typeCount;
+
+    /**
+     * The access flags of this class.
+     */
+    private int access;
+
+    /**
+     * The constant pool item that contains the internal name of this class.
+     */
+    private int name;
+
+    /**
+     * The internal name of this class.
+     */
+    String thisName;
+
+    /**
+     * The constant pool item that contains the signature of this class.
+     */
+    private int signature;
+
+    /**
+     * The constant pool item that contains the internal name of the super class
+     * of this class.
+     */
+    private int superName;
+
+    /**
+     * Number of interfaces implemented or extended by this class or interface.
+     */
+    private int interfaceCount;
+
+    /**
+     * The interfaces implemented or extended by this class or interface. More
+     * precisely, this array contains the indexes of the constant pool items
+     * that contain the internal names of these interfaces.
+     */
+    private int[] interfaces;
+
+    /**
+     * The index of the constant pool item that contains the name of the source
+     * file from which this class was compiled.
+     */
+    private int sourceFile;
+
+    /**
+     * The SourceDebug attribute of this class.
+     */
+    private ByteVector sourceDebug;
+
+    /**
+     * The constant pool item that contains the name of the enclosing class of
+     * this class.
+     */
+    private int enclosingMethodOwner;
+
+    /**
+     * The constant pool item that contains the name and descriptor of the
+     * enclosing method of this class.
+     */
+    private int enclosingMethod;
+
+    /**
+     * The runtime visible annotations of this class.
+     */
+    private AnnotationWriter anns;
+
+    /**
+     * The runtime invisible annotations of this class.
+     */
+    private AnnotationWriter ianns;
+
+    /**
+     * The non standard attributes of this class.
+     */
+    private Attribute attrs;
+
+    /**
+     * The number of entries in the InnerClasses attribute.
+     */
+    private int innerClassesCount;
+
+    /**
+     * The InnerClasses attribute.
+     */
+    private ByteVector innerClasses;
+
+    /**
+     * The number of entries in the BootstrapMethods attribute.
+     */
+    int bootstrapMethodsCount;
+
+    /**
+     * The BootstrapMethods attribute.
+     */
+    ByteVector bootstrapMethods;
+
+    /**
+     * The fields of this class. These fields are stored in a linked list of
+     * {@link FieldWriter} objects, linked to each other by their
+     * {@link FieldWriter#fv} field. This field stores the first element of
+     * this list.
+     */
+    FieldWriter firstField;
+
+    /**
+     * The fields of this class. These fields are stored in a linked list of
+     * {@link FieldWriter} objects, linked to each other by their
+     * {@link FieldWriter#fv} field. This field stores the last element of
+     * this list.
+     */
+    FieldWriter lastField;
+
+    /**
+     * The methods of this class. These methods are stored in a linked list of
+     * {@link MethodWriter} objects, linked to each other by their
+     * {@link MethodWriter#mv} field. This field stores the first element of
+     * this list.
+     */
+    MethodWriter firstMethod;
+
+    /**
+     * The methods of this class. These methods are stored in a linked list of
+     * {@link MethodWriter} objects, linked to each other by their
+     * {@link MethodWriter#mv} field. This field stores the last element of
+     * this list.
+     */
+    MethodWriter lastMethod;
+
+    /**
+     * <tt>true</tt> if the maximum stack size and number of local variables
+     * must be automatically computed.
+     */
+    private final boolean computeMaxs;
+
+    /**
+     * <tt>true</tt> if the stack map frames must be recomputed from scratch.
+     */
+    private final boolean computeFrames;
+
+    /**
+     * <tt>true</tt> if the stack map tables of this class are invalid. The
+     * {@link MethodWriter#resizeInstructions} method cannot transform existing
+     * stack map tables, and so produces potentially invalid classes when it is
+     * executed. In this case the class is reread and rewritten with the
+     * {@link #COMPUTE_FRAMES} option (the resizeInstructions method can resize
+     * stack map tables when this option is used).
+     */
+    boolean invalidFrames;
+
+    // ------------------------------------------------------------------------
+    // Static initializer
+    // ------------------------------------------------------------------------
+
+    /**
+     * Computes the instruction types of JVM opcodes.
+     */
+    static {
+        int i;
+        byte[] b = new byte[220];
+        String s = "AAAAAAAAAAAAAAAABCLMMDDDDDEEEEEEEEEEEEEEEEEEEEAAAAAAAADD"
+                + "DDDEEEEEEEEEEEEEEEEEEEEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA"
+                + "AAAAAAAAAAAAAAAAANAAAAAAAAAAAAAAAAAAAAJJJJJJJJJJJJJJJJDOPAA"
+                + "AAAAGGGGGGGHIFBFAAFFAARQJJKKJJJJJJJJJJJJJJJJJJ";
+        for (i = 0; i < b.length; ++i) {
+            b[i] = (byte) (s.charAt(i) - 'A');
+        }
+        TYPE = b;
+
+        // code to generate the above string
+        //
+        // // SBYTE_INSN instructions
+        // b[Constants.NEWARRAY] = SBYTE_INSN;
+        // b[Constants.BIPUSH] = SBYTE_INSN;
+        //
+        // // SHORT_INSN instructions
+        // b[Constants.SIPUSH] = SHORT_INSN;
+        //
+        // // (IMPL)VAR_INSN instructions
+        // b[Constants.RET] = VAR_INSN;
+        // for (i = Constants.ILOAD; i <= Constants.ALOAD; ++i) {
+        // b[i] = VAR_INSN;
+        // }
+        // for (i = Constants.ISTORE; i <= Constants.ASTORE; ++i) {
+        // b[i] = VAR_INSN;
+        // }
+        // for (i = 26; i <= 45; ++i) { // ILOAD_0 to ALOAD_3
+        // b[i] = IMPLVAR_INSN;
+        // }
+        // for (i = 59; i <= 78; ++i) { // ISTORE_0 to ASTORE_3
+        // b[i] = IMPLVAR_INSN;
+        // }
+        //
+        // // TYPE_INSN instructions
+        // b[Constants.NEW] = TYPE_INSN;
+        // b[Constants.ANEWARRAY] = TYPE_INSN;
+        // b[Constants.CHECKCAST] = TYPE_INSN;
+        // b[Constants.INSTANCEOF] = TYPE_INSN;
+        //
+        // // (Set)FIELDORMETH_INSN instructions
+        // for (i = Constants.GETSTATIC; i <= Constants.INVOKESTATIC; ++i) {
+        // b[i] = FIELDORMETH_INSN;
+        // }
+        // b[Constants.INVOKEINTERFACE] = ITFMETH_INSN;
+        // b[Constants.INVOKEDYNAMIC] = INDYMETH_INSN;
+        //
+        // // LABEL(W)_INSN instructions
+        // for (i = Constants.IFEQ; i <= Constants.JSR; ++i) {
+        // b[i] = LABEL_INSN;
+        // }
+        // b[Constants.IFNULL] = LABEL_INSN;
+        // b[Constants.IFNONNULL] = LABEL_INSN;
+        // b[200] = LABELW_INSN; // GOTO_W
+        // b[201] = LABELW_INSN; // JSR_W
+        // // temporary opcodes used internally by ASM - see Label and
+        // MethodWriter
+        // for (i = 202; i < 220; ++i) {
+        // b[i] = LABEL_INSN;
+        // }
+        //
+        // // LDC(_W) instructions
+        // b[Constants.LDC] = LDC_INSN;
+        // b[19] = LDCW_INSN; // LDC_W
+        // b[20] = LDCW_INSN; // LDC2_W
+        //
+        // // special instructions
+        // b[Constants.IINC] = IINC_INSN;
+        // b[Constants.TABLESWITCH] = TABL_INSN;
+        // b[Constants.LOOKUPSWITCH] = LOOK_INSN;
+        // b[Constants.MULTIANEWARRAY] = MANA_INSN;
+        // b[196] = WIDE_INSN; // WIDE
+        //
+        // for (i = 0; i < b.length; ++i) {
+        // System.err.print((char)('A' + b[i]));
+        // }
+        // System.err.println();
+    }
+
+    // ------------------------------------------------------------------------
+    // Constructor
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a new {@link ClassWriter} object.
+     *
+     * @param flags option flags that can be used to modify the default behavior
+     *        of this class. See {@link #COMPUTE_MAXS}, {@link #COMPUTE_FRAMES}.
+     */
+    public ClassWriter(final int flags) {
+        super(Opcodes.ASM4);
+        index = 1;
+        pool = new ByteVector();
+        items = new Item[256];
+        threshold = (int) (0.75d * items.length);
+        key = new Item();
+        key2 = new Item();
+        key3 = new Item();
+        key4 = new Item();
+        this.computeMaxs = (flags & COMPUTE_MAXS) != 0;
+        this.computeFrames = (flags & COMPUTE_FRAMES) != 0;
+    }
+
+    /**
+     * Constructs a new {@link ClassWriter} object and enables optimizations for
+     * "mostly add" bytecode transformations. These optimizations are the
+     * following:
+     *
+     * <ul> <li>The constant pool from the original class is copied as is in the
+     * new class, which saves time. New constant pool entries will be added at
+     * the end if necessary, but unused constant pool entries <i>won't be
+     * removed</i>.</li> <li>Methods that are not transformed are copied as is
+     * in the new class, directly from the original class bytecode (i.e. without
+     * emitting visit events for all the method instructions), which saves a
+     * <i>lot</i> of time. Untransformed methods are detected by the fact that
+     * the {@link ClassReader} receives {@link MethodVisitor} objects that come
+     * from a {@link ClassWriter} (and not from any other {@link ClassVisitor}
+     * instance).</li> </ul>
+     *
+     * @param classReader the {@link ClassReader} used to read the original
+     *        class. It will be used to copy the entire constant pool from the
+     *        original class and also to copy other fragments of original
+     *        bytecode where applicable.
+     * @param flags option flags that can be used to modify the default behavior
+     *        of this class. <i>These option flags do not affect methods that
+     *        are copied as is in the new class. This means that the maximum
+     *        stack size nor the stack frames will be computed for these
+     *        methods</i>. See {@link #COMPUTE_MAXS}, {@link #COMPUTE_FRAMES}.
+     */
+    public ClassWriter(final ClassReader classReader, final int flags) {
+        this(flags);
+        classReader.copyPool(this);
+        this.cr = classReader;
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the ClassVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public final void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        this.version = version;
+        this.access = access;
+        this.name = newClass(name);
+        thisName = name;
+        if (ClassReader.SIGNATURES && signature != null) {
+            this.signature = newUTF8(signature);
+        }
+        this.superName = superName == null ? 0 : newClass(superName);
+        if (interfaces != null && interfaces.length > 0) {
+            interfaceCount = interfaces.length;
+            this.interfaces = new int[interfaceCount];
+            for (int i = 0; i < interfaceCount; ++i) {
+                this.interfaces[i] = newClass(interfaces[i]);
+            }
+        }
+    }
+
+    @Override
+    public final void visitSource(final String file, final String debug) {
+        if (file != null) {
+            sourceFile = newUTF8(file);
+        }
+        if (debug != null) {
+            sourceDebug = new ByteVector().putUTF8(debug);
+        }
+    }
+
+    @Override
+    public final void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        enclosingMethodOwner = newClass(owner);
+        if (name != null && desc != null) {
+            enclosingMethod = newNameType(name, desc);
+        }
+    }
+
+    @Override
+    public final AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        if (!ClassReader.ANNOTATIONS) {
+            return null;
+        }
+        ByteVector bv = new ByteVector();
+        // write type, and reserve space for values count
+        bv.putShort(newUTF8(desc)).putShort(0);
+        AnnotationWriter aw = new AnnotationWriter(this, true, bv, bv, 2);
+        if (visible) {
+            aw.next = anns;
+            anns = aw;
+        } else {
+            aw.next = ianns;
+            ianns = aw;
+        }
+        return aw;
+    }
+
+    @Override
+    public final void visitAttribute(final Attribute attr) {
+        attr.next = attrs;
+        attrs = attr;
+    }
+
+    @Override
+    public final void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        if (innerClasses == null) {
+            innerClasses = new ByteVector();
+        }
+        ++innerClassesCount;
+        innerClasses.putShort(name == null ? 0 : newClass(name));
+        innerClasses.putShort(outerName == null ? 0 : newClass(outerName));
+        innerClasses.putShort(innerName == null ? 0 : newUTF8(innerName));
+        innerClasses.putShort(access);
+    }
+
+    @Override
+    public final FieldVisitor visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        return new FieldWriter(this, access, name, desc, signature, value);
+    }
+
+    @Override
+    public final MethodVisitor visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        return new MethodWriter(this,
+                access,
+                name,
+                desc,
+                signature,
+                exceptions,
+                computeMaxs,
+                computeFrames);
+    }
+
+    @Override
+    public final void visitEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Other public methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the bytecode of the class that was build with this class writer.
+     *
+     * @return the bytecode of the class that was build with this class writer.
+     */
+    public byte[] toByteArray() {
+        if (index > Short.MAX_VALUE) {
+            throw new RuntimeException("Class file too large!");
+        }
+        // computes the real size of the bytecode of this class
+        int size = 24 + 2 * interfaceCount;
+        int nbFields = 0;
+        FieldWriter fb = firstField;
+        while (fb != null) {
+            ++nbFields;
+            size += fb.getSize();
+            fb = (FieldWriter) fb.fv;
+        }
+        int nbMethods = 0;
+        MethodWriter mb = firstMethod;
+        while (mb != null) {
+            ++nbMethods;
+            size += mb.getSize();
+            mb = (MethodWriter) mb.mv;
+        }
+        int attributeCount = 0;
+        if (bootstrapMethods != null) {  // we put it as first argument in order
+                                         // to improve a bit ClassReader.copyBootstrapMethods
+            ++attributeCount;
+            size += 8 + bootstrapMethods.length;
+            newUTF8("BootstrapMethods");
+        }
+        if (ClassReader.SIGNATURES && signature != 0) {
+            ++attributeCount;
+            size += 8;
+            newUTF8("Signature");
+        }
+        if (sourceFile != 0) {
+            ++attributeCount;
+            size += 8;
+            newUTF8("SourceFile");
+        }
+        if (sourceDebug != null) {
+            ++attributeCount;
+            size += sourceDebug.length + 4;
+            newUTF8("SourceDebugExtension");
+        }
+        if (enclosingMethodOwner != 0) {
+            ++attributeCount;
+            size += 10;
+            newUTF8("EnclosingMethod");
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            ++attributeCount;
+            size += 6;
+            newUTF8("Deprecated");
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((version & 0xFFFF) < Opcodes.V1_5 || (access & ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            ++attributeCount;
+            size += 6;
+            newUTF8("Synthetic");
+        }
+        if (innerClasses != null) {
+            ++attributeCount;
+            size += 8 + innerClasses.length;
+            newUTF8("InnerClasses");
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            ++attributeCount;
+            size += 8 + anns.getSize();
+            newUTF8("RuntimeVisibleAnnotations");
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            ++attributeCount;
+            size += 8 + ianns.getSize();
+            newUTF8("RuntimeInvisibleAnnotations");
+        }
+        if (attrs != null) {
+            attributeCount += attrs.getCount();
+            size += attrs.getSize(this, null, 0, -1, -1);
+        }
+        size += pool.length;
+        // allocates a byte vector of this size, in order to avoid unnecessary
+        // arraycopy operations in the ByteVector.enlarge() method
+        ByteVector out = new ByteVector(size);
+        out.putInt(0xCAFEBABE).putInt(version);
+        out.putShort(index).putByteArray(pool.data, 0, pool.length);
+        int mask = Opcodes.ACC_DEPRECATED
+                | ClassWriter.ACC_SYNTHETIC_ATTRIBUTE
+                | ((access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) / (ClassWriter.ACC_SYNTHETIC_ATTRIBUTE / Opcodes.ACC_SYNTHETIC));
+        out.putShort(access & ~mask).putShort(name).putShort(superName);
+        out.putShort(interfaceCount);
+        for (int i = 0; i < interfaceCount; ++i) {
+            out.putShort(interfaces[i]);
+        }
+        out.putShort(nbFields);
+        fb = firstField;
+        while (fb != null) {
+            fb.put(out);
+            fb = (FieldWriter) fb.fv;
+        }
+        out.putShort(nbMethods);
+        mb = firstMethod;
+        while (mb != null) {
+            mb.put(out);
+            mb = (MethodWriter) mb.mv;
+        }
+        out.putShort(attributeCount);
+        if (bootstrapMethods != null) {   // should be the first class attribute ?
+            out.putShort(newUTF8("BootstrapMethods"));
+            out.putInt(bootstrapMethods.length + 2).putShort(bootstrapMethodsCount);
+            out.putByteArray(bootstrapMethods.data, 0, bootstrapMethods.length);
+        }
+        if (ClassReader.SIGNATURES && signature != 0) {
+            out.putShort(newUTF8("Signature")).putInt(2).putShort(signature);
+        }
+        if (sourceFile != 0) {
+            out.putShort(newUTF8("SourceFile")).putInt(2).putShort(sourceFile);
+        }
+        if (sourceDebug != null) {
+            int len = sourceDebug.length - 2;
+            out.putShort(newUTF8("SourceDebugExtension")).putInt(len);
+            out.putByteArray(sourceDebug.data, 2, len);
+        }
+        if (enclosingMethodOwner != 0) {
+            out.putShort(newUTF8("EnclosingMethod")).putInt(4);
+            out.putShort(enclosingMethodOwner).putShort(enclosingMethod);
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            out.putShort(newUTF8("Deprecated")).putInt(0);
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((version & 0xFFFF) < Opcodes.V1_5 || (access & ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            out.putShort(newUTF8("Synthetic")).putInt(0);
+        }
+        if (innerClasses != null) {
+            out.putShort(newUTF8("InnerClasses"));
+            out.putInt(innerClasses.length + 2).putShort(innerClassesCount);
+            out.putByteArray(innerClasses.data, 0, innerClasses.length);
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            out.putShort(newUTF8("RuntimeVisibleAnnotations"));
+            anns.put(out);
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            out.putShort(newUTF8("RuntimeInvisibleAnnotations"));
+            ianns.put(out);
+        }
+        if (attrs != null) {
+            attrs.put(this, null, 0, -1, -1, out);
+        }
+        if (invalidFrames) {
+            ClassWriter cw = new ClassWriter(COMPUTE_FRAMES);
+            new ClassReader(out.data).accept(cw, ClassReader.SKIP_FRAMES);
+            return cw.toByteArray();
+        }
+        return out.data;
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods: constant pool management
+    // ------------------------------------------------------------------------
+
+    /**
+     * Adds a number or string constant to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     *
+     * @param cst the value of the constant to be added to the constant pool.
+     *        This parameter must be an {@link Integer}, a {@link Float}, a
+     *        {@link Long}, a {@link Double}, a {@link String} or a
+     *        {@link Type}.
+     * @return a new or already existing constant item with the given value.
+     */
+    Item newConstItem(final Object cst) {
+        if (cst instanceof Integer) {
+            int val = ((Integer) cst).intValue();
+            return newInteger(val);
+        } else if (cst instanceof Byte) {
+            int val = ((Byte) cst).intValue();
+            return newInteger(val);
+        } else if (cst instanceof Character) {
+            int val = ((Character) cst).charValue();
+            return newInteger(val);
+        } else if (cst instanceof Short) {
+            int val = ((Short) cst).intValue();
+            return newInteger(val);
+        } else if (cst instanceof Boolean) {
+            int val = ((Boolean) cst).booleanValue() ? 1 : 0;
+            return newInteger(val);
+        } else if (cst instanceof Float) {
+            float val = ((Float) cst).floatValue();
+            return newFloat(val);
+        } else if (cst instanceof Long) {
+            long val = ((Long) cst).longValue();
+            return newLong(val);
+        } else if (cst instanceof Double) {
+            double val = ((Double) cst).doubleValue();
+            return newDouble(val);
+        } else if (cst instanceof String) {
+            return newString((String) cst);
+        } else if (cst instanceof Type) {
+            Type t = (Type) cst;
+            int s = t.getSort();
+            if (s == Type.ARRAY) {
+                return newClassItem(t.getDescriptor());
+            } else if (s == Type.OBJECT) {
+                return newClassItem(t.getInternalName());
+            } else { // s == Type.METHOD
+                return newMethodTypeItem(t.getDescriptor());
+            }
+        } else if (cst instanceof Handle) {
+            Handle h = (Handle) cst;
+            return newHandleItem(h.tag, h.owner, h.name, h.desc);
+        } else {
+            throw new IllegalArgumentException("value " + cst);
+        }
+    }
+
+    /**
+     * Adds a number or string constant to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param cst the value of the constant to be added to the constant pool.
+     *        This parameter must be an {@link Integer}, a {@link Float}, a
+     *        {@link Long}, a {@link Double} or a {@link String}.
+     * @return the index of a new or already existing constant item with the
+     *         given value.
+     */
+    public int newConst(final Object cst) {
+        return newConstItem(cst).index;
+    }
+
+    /**
+     * Adds an UTF8 string to the constant pool of the class being build. Does
+     * nothing if the constant pool already contains a similar item. <i>This
+     * method is intended for {@link Attribute} sub classes, and is normally not
+     * needed by class generators or adapters.</i>
+     *
+     * @param value the String value.
+     * @return the index of a new or already existing UTF8 item.
+     */
+    public int newUTF8(final String value) {
+        key.set(UTF8, value, null, null);
+        Item result = get(key);
+        if (result == null) {
+            pool.putByte(UTF8).putUTF8(value);
+            result = new Item(index++, key);
+            put(result);
+        }
+        return result.index;
+    }
+
+    /**
+     * Adds a class reference to the constant pool of the class being build.
+     * Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param value the internal name of the class.
+     * @return a new or already existing class reference item.
+     */
+    Item newClassItem(final String value) {
+        key2.set(CLASS, value, null, null);
+        Item result = get(key2);
+        if (result == null) {
+            pool.put12(CLASS, newUTF8(value));
+            result = new Item(index++, key2);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a class reference to the constant pool of the class being build.
+     * Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param value the internal name of the class.
+     * @return the index of a new or already existing class reference item.
+     */
+    public int newClass(final String value) {
+        return newClassItem(value).index;
+    }
+
+    /**
+     * Adds a method type reference to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param methodDesc method descriptor of the method type.
+     * @return a new or already existing method type reference item.
+     */
+    Item newMethodTypeItem(final String methodDesc) {
+        key2.set(MTYPE, methodDesc, null, null);
+        Item result = get(key2);
+        if (result == null) {
+            pool.put12(MTYPE, newUTF8(methodDesc));
+            result = new Item(index++, key2);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a method type reference to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param methodDesc method descriptor of the method type.
+     * @return the index of a new or already existing method type reference
+     *         item.
+     */
+    public int newMethodType(final String methodDesc) {
+        return newMethodTypeItem(methodDesc).index;
+    }
+
+    /**
+     * Adds a handle to the constant pool of the class being build. Does nothing
+     * if the constant pool already contains a similar item. <i>This method is
+     * intended for {@link Attribute} sub classes, and is normally not needed by
+     * class generators or adapters.</i>
+     *
+     * @param tag the kind of this handle. Must be {@link Opcodes#H_GETFIELD},
+     *        {@link Opcodes#H_GETSTATIC}, {@link Opcodes#H_PUTFIELD},
+     *        {@link Opcodes#H_PUTSTATIC}, {@link Opcodes#H_INVOKEVIRTUAL},
+     *        {@link Opcodes#H_INVOKESTATIC}, {@link Opcodes#H_INVOKESPECIAL},
+     *        {@link Opcodes#H_NEWINVOKESPECIAL} or
+     *        {@link Opcodes#H_INVOKEINTERFACE}.
+     * @param owner the internal name of the field or method owner class.
+     * @param name the name of the field or method.
+     * @param desc the descriptor of the field or method.
+     * @return a new or an already existing method type reference item.
+     */
+    Item newHandleItem(
+        final int tag,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        key4.set(HANDLE_BASE + tag, owner, name, desc);
+        Item result = get(key4);
+        if (result == null) {
+            if (tag <= Opcodes.H_PUTSTATIC) {
+                put112(HANDLE, tag, newField(owner, name, desc));
+            } else {
+                put112(HANDLE, tag, newMethod(owner,
+                        name,
+                        desc,
+                        tag == Opcodes.H_INVOKEINTERFACE));
+            }
+            result = new Item(index++, key4);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a handle to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param tag the kind of this handle. Must be {@link Opcodes#H_GETFIELD},
+     *        {@link Opcodes#H_GETSTATIC}, {@link Opcodes#H_PUTFIELD},
+     *        {@link Opcodes#H_PUTSTATIC}, {@link Opcodes#H_INVOKEVIRTUAL},
+     *        {@link Opcodes#H_INVOKESTATIC}, {@link Opcodes#H_INVOKESPECIAL},
+     *        {@link Opcodes#H_NEWINVOKESPECIAL} or
+     *        {@link Opcodes#H_INVOKEINTERFACE}.
+     * @param owner the internal name of the field or method owner class.
+     * @param name the name of the field or method.
+     * @param desc the descriptor of the field or method.
+     * @return the index of a new or already existing method type reference
+     *         item.
+     */
+    public int newHandle(
+        final int tag,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        return newHandleItem(tag, owner, name, desc).index;
+    }
+
+    /**
+     * Adds an invokedynamic reference to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param name name of the invoked method.
+     * @param desc descriptor of the invoke method.
+     * @param bsm the bootstrap method.
+     * @param bsmArgs the bootstrap method constant arguments.
+     *
+     * @return a new or an already existing invokedynamic type reference item.
+     */
+    Item newInvokeDynamicItem(
+        final String name,
+        final String desc,
+        final Handle bsm,
+        final Object... bsmArgs)
+    {
+        // cache for performance
+        ByteVector bootstrapMethods = this.bootstrapMethods;
+        if (bootstrapMethods == null) {
+            bootstrapMethods = this.bootstrapMethods = new ByteVector();
+        }
+
+        int position = bootstrapMethods.length; // record current position
+
+        int hashCode = bsm.hashCode();
+        bootstrapMethods.putShort(newHandle(bsm.tag,
+                bsm.owner,
+                bsm.name,
+                bsm.desc));
+
+        int argsLength = bsmArgs.length;
+        bootstrapMethods.putShort(argsLength);
+
+        for (int i = 0; i < argsLength; i++) {
+            Object bsmArg = bsmArgs[i];
+            hashCode ^= bsmArg.hashCode();
+            bootstrapMethods.putShort(newConst(bsmArg));
+        }
+
+        byte[] data = bootstrapMethods.data;
+        int length = (1 + 1 + argsLength) << 1; // (bsm + argCount + arguments)
+        hashCode &= 0x7FFFFFFF;
+        Item result = items[hashCode % items.length];
+        loop: while (result != null) {
+            if (result.type != BSM || result.hashCode != hashCode) {
+                result = result.next;
+                continue;
+            }
+
+            // because the data encode the size of the argument
+            // we don't need to test if these size are equals
+            int resultPosition = result.intVal;
+            for (int p = 0; p < length; p++) {
+                if (data[position + p] != data[resultPosition + p]) {
+                    result = result.next;
+                    continue loop;
+                }
+            }
+            break;
+        }
+
+        int bootstrapMethodIndex;
+        if (result != null) {
+            bootstrapMethodIndex = result.index;
+            bootstrapMethods.length = position; // revert to old position
+        } else {
+            bootstrapMethodIndex = bootstrapMethodsCount++;
+            result = new Item(bootstrapMethodIndex);
+            result.set(position, hashCode);
+            put(result);
+        }
+
+        // now, create the InvokeDynamic constant
+        key3.set(name, desc, bootstrapMethodIndex);
+        result = get(key3);
+        if (result == null) {
+            put122(INDY, bootstrapMethodIndex, newNameType(name, desc));
+            result = new Item(index++, key3);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds an invokedynamic reference to the constant pool of the class being
+     * build. Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param name name of the invoked method.
+     * @param desc descriptor of the invoke method.
+     * @param bsm the bootstrap method.
+     * @param bsmArgs the bootstrap method constant arguments.
+     *
+     * @return the index of a new or already existing invokedynamic
+     *         reference item.
+     */
+    public int newInvokeDynamic(
+        final String name,
+        final String desc,
+        final Handle bsm,
+        final Object... bsmArgs)
+    {
+        return newInvokeDynamicItem(name, desc, bsm, bsmArgs).index;
+    }
+
+    /**
+     * Adds a field reference to the constant pool of the class being build.
+     * Does nothing if the constant pool already contains a similar item.
+     *
+     * @param owner the internal name of the field's owner class.
+     * @param name the field's name.
+     * @param desc the field's descriptor.
+     * @return a new or already existing field reference item.
+     */
+    Item newFieldItem(final String owner, final String name, final String desc)
+    {
+        key3.set(FIELD, owner, name, desc);
+        Item result = get(key3);
+        if (result == null) {
+            put122(FIELD, newClass(owner), newNameType(name, desc));
+            result = new Item(index++, key3);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a field reference to the constant pool of the class being build.
+     * Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param owner the internal name of the field's owner class.
+     * @param name the field's name.
+     * @param desc the field's descriptor.
+     * @return the index of a new or already existing field reference item.
+     */
+    public int newField(final String owner, final String name, final String desc)
+    {
+        return newFieldItem(owner, name, desc).index;
+    }
+
+    /**
+     * Adds a method reference to the constant pool of the class being build.
+     * Does nothing if the constant pool already contains a similar item.
+     *
+     * @param owner the internal name of the method's owner class.
+     * @param name the method's name.
+     * @param desc the method's descriptor.
+     * @param itf <tt>true</tt> if <tt>owner</tt> is an interface.
+     * @return a new or already existing method reference item.
+     */
+    Item newMethodItem(
+        final String owner,
+        final String name,
+        final String desc,
+        final boolean itf)
+    {
+        int type = itf ? IMETH : METH;
+        key3.set(type, owner, name, desc);
+        Item result = get(key3);
+        if (result == null) {
+            put122(type, newClass(owner), newNameType(name, desc));
+            result = new Item(index++, key3);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a method reference to the constant pool of the class being build.
+     * Does nothing if the constant pool already contains a similar item.
+     * <i>This method is intended for {@link Attribute} sub classes, and is
+     * normally not needed by class generators or adapters.</i>
+     *
+     * @param owner the internal name of the method's owner class.
+     * @param name the method's name.
+     * @param desc the method's descriptor.
+     * @param itf <tt>true</tt> if <tt>owner</tt> is an interface.
+     * @return the index of a new or already existing method reference item.
+     */
+    public int newMethod(
+        final String owner,
+        final String name,
+        final String desc,
+        final boolean itf)
+    {
+        return newMethodItem(owner, name, desc, itf).index;
+    }
+
+    /**
+     * Adds an integer to the constant pool of the class being build. Does
+     * nothing if the constant pool already contains a similar item.
+     *
+     * @param value the int value.
+     * @return a new or already existing int item.
+     */
+    Item newInteger(final int value) {
+        key.set(value);
+        Item result = get(key);
+        if (result == null) {
+            pool.putByte(INT).putInt(value);
+            result = new Item(index++, key);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a float to the constant pool of the class being build. Does nothing
+     * if the constant pool already contains a similar item.
+     *
+     * @param value the float value.
+     * @return a new or already existing float item.
+     */
+    Item newFloat(final float value) {
+        key.set(value);
+        Item result = get(key);
+        if (result == null) {
+            pool.putByte(FLOAT).putInt(key.intVal);
+            result = new Item(index++, key);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a long to the constant pool of the class being build. Does nothing
+     * if the constant pool already contains a similar item.
+     *
+     * @param value the long value.
+     * @return a new or already existing long item.
+     */
+    Item newLong(final long value) {
+        key.set(value);
+        Item result = get(key);
+        if (result == null) {
+            pool.putByte(LONG).putLong(value);
+            result = new Item(index, key);
+            index += 2;
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a double to the constant pool of the class being build. Does nothing
+     * if the constant pool already contains a similar item.
+     *
+     * @param value the double value.
+     * @return a new or already existing double item.
+     */
+    Item newDouble(final double value) {
+        key.set(value);
+        Item result = get(key);
+        if (result == null) {
+            pool.putByte(DOUBLE).putLong(key.longVal);
+            result = new Item(index, key);
+            index += 2;
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a string to the constant pool of the class being build. Does nothing
+     * if the constant pool already contains a similar item.
+     *
+     * @param value the String value.
+     * @return a new or already existing string item.
+     */
+    private Item newString(final String value) {
+        key2.set(STR, value, null, null);
+        Item result = get(key2);
+        if (result == null) {
+            pool.put12(STR, newUTF8(value));
+            result = new Item(index++, key2);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds a name and type to the constant pool of the class being build. Does
+     * nothing if the constant pool already contains a similar item. <i>This
+     * method is intended for {@link Attribute} sub classes, and is normally not
+     * needed by class generators or adapters.</i>
+     *
+     * @param name a name.
+     * @param desc a type descriptor.
+     * @return the index of a new or already existing name and type item.
+     */
+    public int newNameType(final String name, final String desc) {
+        return newNameTypeItem(name, desc).index;
+    }
+
+    /**
+     * Adds a name and type to the constant pool of the class being build. Does
+     * nothing if the constant pool already contains a similar item.
+     *
+     * @param name a name.
+     * @param desc a type descriptor.
+     * @return a new or already existing name and type item.
+     */
+    Item newNameTypeItem(final String name, final String desc) {
+        key2.set(NAME_TYPE, name, desc, null);
+        Item result = get(key2);
+        if (result == null) {
+            put122(NAME_TYPE, newUTF8(name), newUTF8(desc));
+            result = new Item(index++, key2);
+            put(result);
+        }
+        return result;
+    }
+
+    /**
+     * Adds the given internal name to {@link #typeTable} and returns its index.
+     * Does nothing if the type table already contains this internal name.
+     *
+     * @param type the internal name to be added to the type table.
+     * @return the index of this internal name in the type table.
+     */
+    int addType(final String type) {
+        key.set(TYPE_NORMAL, type, null, null);
+        Item result = get(key);
+        if (result == null) {
+            result = addType(key);
+        }
+        return result.index;
+    }
+
+    /**
+     * Adds the given "uninitialized" type to {@link #typeTable} and returns its
+     * index. This method is used for UNINITIALIZED types, made of an internal
+     * name and a bytecode offset.
+     *
+     * @param type the internal name to be added to the type table.
+     * @param offset the bytecode offset of the NEW instruction that created
+     *        this UNINITIALIZED type value.
+     * @return the index of this internal name in the type table.
+     */
+    int addUninitializedType(final String type, final int offset) {
+        key.type = TYPE_UNINIT;
+        key.intVal = offset;
+        key.strVal1 = type;
+        key.hashCode = 0x7FFFFFFF & (TYPE_UNINIT + type.hashCode() + offset);
+        Item result = get(key);
+        if (result == null) {
+            result = addType(key);
+        }
+        return result.index;
+    }
+
+    /**
+     * Adds the given Item to {@link #typeTable}.
+     *
+     * @param item the value to be added to the type table.
+     * @return the added Item, which a new Item instance with the same value as
+     *         the given Item.
+     */
+    private Item addType(final Item item) {
+        ++typeCount;
+        Item result = new Item(typeCount, key);
+        put(result);
+        if (typeTable == null) {
+            typeTable = new Item[16];
+        }
+        if (typeCount == typeTable.length) {
+            Item[] newTable = new Item[2 * typeTable.length];
+            System.arraycopy(typeTable, 0, newTable, 0, typeTable.length);
+            typeTable = newTable;
+        }
+        typeTable[typeCount] = result;
+        return result;
+    }
+
+    /**
+     * Returns the index of the common super type of the two given types. This
+     * method calls {@link #getCommonSuperClass} and caches the result in the
+     * {@link #items} hash table to speedup future calls with the same
+     * parameters.
+     *
+     * @param type1 index of an internal name in {@link #typeTable}.
+     * @param type2 index of an internal name in {@link #typeTable}.
+     * @return the index of the common super type of the two given types.
+     */
+    int getMergedType(final int type1, final int type2) {
+        key2.type = TYPE_MERGED;
+        key2.longVal = type1 | (((long) type2) << 32);
+        key2.hashCode = 0x7FFFFFFF & (TYPE_MERGED + type1 + type2);
+        Item result = get(key2);
+        if (result == null) {
+            String t = typeTable[type1].strVal1;
+            String u = typeTable[type2].strVal1;
+            key2.intVal = addType(getCommonSuperClass(t, u));
+            result = new Item((short) 0, key2);
+            put(result);
+        }
+        return result.intVal;
+    }
+
+    /**
+     * Returns the common super type of the two given types. The default
+     * implementation of this method <i>loads<i> the two given classes and uses
+     * the java.lang.Class methods to find the common super class. It can be
+     * overridden to compute this common super type in other ways, in particular
+     * without actually loading any class, or to take into account the class
+     * that is currently being generated by this ClassWriter, which can of
+     * course not be loaded since it is under construction.
+     *
+     * @param type1 the internal name of a class.
+     * @param type2 the internal name of another class.
+     * @return the internal name of the common super class of the two given
+     *         classes.
+     */
+    protected String getCommonSuperClass(final String type1, final String type2)
+    {
+        Class<?> c, d;
+        ClassLoader classLoader = getClass().getClassLoader();
+        try {
+            c = Class.forName(type1.replace('/', '.'), false, classLoader);
+            d = Class.forName(type2.replace('/', '.'), false, classLoader);
+        } catch (Exception e) {
+            throw new RuntimeException(e.toString());
+        }
+        if (c.isAssignableFrom(d)) {
+            return type1;
+        }
+        if (d.isAssignableFrom(c)) {
+            return type2;
+        }
+        if (c.isInterface() || d.isInterface()) {
+            return "java/lang/Object";
+        } else {
+            do {
+                c = c.getSuperclass();
+            } while (!c.isAssignableFrom(d));
+            return c.getName().replace('.', '/');
+        }
+    }
+
+    /**
+     * Returns the constant pool's hash table item which is equal to the given
+     * item.
+     *
+     * @param key a constant pool item.
+     * @return the constant pool's hash table item which is equal to the given
+     *         item, or <tt>null</tt> if there is no such item.
+     */
+    private Item get(final Item key) {
+        Item i = items[key.hashCode % items.length];
+        while (i != null && (i.type != key.type || !key.isEqualTo(i))) {
+            i = i.next;
+        }
+        return i;
+    }
+
+    /**
+     * Puts the given item in the constant pool's hash table. The hash table
+     * <i>must</i> not already contains this item.
+     *
+     * @param i the item to be added to the constant pool's hash table.
+     */
+    private void put(final Item i) {
+        if (index + typeCount > threshold) {
+            int ll = items.length;
+            int nl = ll * 2 + 1;
+            Item[] newItems = new Item[nl];
+            for (int l = ll - 1; l >= 0; --l) {
+                Item j = items[l];
+                while (j != null) {
+                    int index = j.hashCode % newItems.length;
+                    Item k = j.next;
+                    j.next = newItems[index];
+                    newItems[index] = j;
+                    j = k;
+                }
+            }
+            items = newItems;
+            threshold = (int) (nl * 0.75);
+        }
+        int index = i.hashCode % items.length;
+        i.next = items[index];
+        items[index] = i;
+    }
+
+    /**
+     * Puts one byte and two shorts into the constant pool.
+     *
+     * @param b a byte.
+     * @param s1 a short.
+     * @param s2 another short.
+     */
+    private void put122(final int b, final int s1, final int s2) {
+        pool.put12(b, s1).putShort(s2);
+    }
+
+    /**
+     * Puts two bytes and one short into the constant pool.
+     *
+     * @param b1 a byte.
+     * @param b2 another byte.
+     * @param s a short.
+     */
+    private void put112(final int b1, final int b2, final int s) {
+        pool.put11(b1, b2).putShort(s);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Edge.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,104 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * An edge in the control flow graph of a method body. See {@link Label Label}.
+ *
+ * @author Eric Bruneton
+ */
+class Edge {
+
+    /**
+     * Denotes a normal control flow graph edge.
+     */
+    static final int NORMAL = 0;
+
+    /**
+     * Denotes a control flow graph edge corresponding to an exception handler.
+     * More precisely any {@link Edge} whose {@link #info} is strictly positive
+     * corresponds to an exception handler. The actual value of {@link #info} is
+     * the index, in the {@link ClassWriter} type table, of the exception that
+     * is catched.
+     */
+    static final int EXCEPTION = 0x7FFFFFFF;
+
+    /**
+     * Information about this control flow graph edge. If
+     * {@link ClassWriter#COMPUTE_MAXS} is used this field is the (relative)
+     * stack size in the basic block from which this edge originates. This size
+     * is equal to the stack size at the "jump" instruction to which this edge
+     * corresponds, relatively to the stack size at the beginning of the
+     * originating basic block. If {@link ClassWriter#COMPUTE_FRAMES} is used,
+     * this field is the kind of this control flow graph edge (i.e. NORMAL or
+     * EXCEPTION).
+     */
+    int info;
+
+    /**
+     * The successor block of the basic block from which this edge originates.
+     */
+    Label successor;
+
+    /**
+     * The next edge in the list of successors of the originating basic block.
+     * See {@link Label#successors successors}.
+     */
+    Edge next;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/FieldVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,144 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A visitor to visit a Java field. The methods of this class must be called
+ * in the following order: ( <tt>visitAnnotation</tt> |
+ * <tt>visitAttribute</tt> )* <tt>visitEnd</tt>.
+ *
+ * @author Eric Bruneton
+ */
+public abstract class FieldVisitor {
+
+    /**
+     * The ASM API version implemented by this visitor. The value of this field
+     * must be one of {@link Opcodes#ASM4}.
+     */
+    protected final int api;
+
+    /**
+     * The field visitor to which this visitor must delegate method calls. May
+     * be null.
+     */
+    protected FieldVisitor fv;
+
+    /**
+     * Constructs a new {@link FieldVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public FieldVisitor(final int api) {
+        this(api, null);
+    }
+
+    /**
+     * Constructs a new {@link FieldVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param fv the field visitor to which this visitor must delegate method
+     *        calls. May be null.
+     */
+    public FieldVisitor(final int api, final FieldVisitor fv) {
+        /*if (api != Opcodes.ASM4) {
+            throw new IllegalArgumentException();
+        }*/
+        this.api = api;
+        this.fv = fv;
+    }
+
+    /**
+     * Visits an annotation of the field.
+     *
+     * @param desc the class descriptor of the annotation class.
+     * @param visible <tt>true</tt> if the annotation is visible at runtime.
+     * @return a visitor to visit the annotation values, or <tt>null</tt> if
+     *         this visitor is not interested in visiting this annotation.
+     */
+    public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
+        if (fv != null) {
+            return fv.visitAnnotation(desc, visible);
+        }
+        return null;
+    }
+
+    /**
+     * Visits a non standard attribute of the field.
+     *
+     * @param attr an attribute.
+     */
+    public void visitAttribute(Attribute attr) {
+        if (fv != null) {
+            fv.visitAttribute(attr);
+        }
+    }
+
+    /**
+     * Visits the end of the field. This method, which is the last one to be
+     * called, is used to inform the visitor that all the annotations and
+     * attributes of the field have been visited.
+     */
+    public void visitEnd() {
+        if (fv != null) {
+            fv.visitEnd();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/FieldWriter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,300 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * An {@link FieldVisitor} that generates Java fields in bytecode form.
+ *
+ * @author Eric Bruneton
+ */
+final class FieldWriter extends FieldVisitor {
+
+    /**
+     * The class writer to which this field must be added.
+     */
+    private final ClassWriter cw;
+
+    /**
+     * Access flags of this field.
+     */
+    private final int access;
+
+    /**
+     * The index of the constant pool item that contains the name of this
+     * method.
+     */
+    private final int name;
+
+    /**
+     * The index of the constant pool item that contains the descriptor of this
+     * field.
+     */
+    private final int desc;
+
+    /**
+     * The index of the constant pool item that contains the signature of this
+     * field.
+     */
+    private int signature;
+
+    /**
+     * The index of the constant pool item that contains the constant value of
+     * this field.
+     */
+    private int value;
+
+    /**
+     * The runtime visible annotations of this field. May be <tt>null</tt>.
+     */
+    private AnnotationWriter anns;
+
+    /**
+     * The runtime invisible annotations of this field. May be <tt>null</tt>.
+     */
+    private AnnotationWriter ianns;
+
+    /**
+     * The non standard attributes of this field. May be <tt>null</tt>.
+     */
+    private Attribute attrs;
+
+    // ------------------------------------------------------------------------
+    // Constructor
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a new {@link FieldWriter}.
+     *
+     * @param cw the class writer to which this field must be added.
+     * @param access the field's access flags (see {@link Opcodes}).
+     * @param name the field's name.
+     * @param desc the field's descriptor (see {@link Type}).
+     * @param signature the field's signature. May be <tt>null</tt>.
+     * @param value the field's constant value. May be <tt>null</tt>.
+     */
+    FieldWriter(
+        final ClassWriter cw,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        super(Opcodes.ASM4);
+        if (cw.firstField == null) {
+            cw.firstField = this;
+        } else {
+            cw.lastField.fv = this;
+        }
+        cw.lastField = this;
+        this.cw = cw;
+        this.access = access;
+        this.name = cw.newUTF8(name);
+        this.desc = cw.newUTF8(desc);
+        if (ClassReader.SIGNATURES && signature != null) {
+            this.signature = cw.newUTF8(signature);
+        }
+        if (value != null) {
+            this.value = cw.newConstItem(value).index;
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the FieldVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        if (!ClassReader.ANNOTATIONS) {
+            return null;
+        }
+        ByteVector bv = new ByteVector();
+        // write type, and reserve space for values count
+        bv.putShort(cw.newUTF8(desc)).putShort(0);
+        AnnotationWriter aw = new AnnotationWriter(cw, true, bv, bv, 2);
+        if (visible) {
+            aw.next = anns;
+            anns = aw;
+        } else {
+            aw.next = ianns;
+            ianns = aw;
+        }
+        return aw;
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        attr.next = attrs;
+        attrs = attr;
+    }
+
+    @Override
+    public void visitEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the size of this field.
+     *
+     * @return the size of this field.
+     */
+    int getSize() {
+        int size = 8;
+        if (value != 0) {
+            cw.newUTF8("ConstantValue");
+            size += 8;
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((cw.version & 0xFFFF) < Opcodes.V1_5 || (access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            cw.newUTF8("Synthetic");
+            size += 6;
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            cw.newUTF8("Deprecated");
+            size += 6;
+        }
+        if (ClassReader.SIGNATURES && signature != 0) {
+            cw.newUTF8("Signature");
+            size += 8;
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            cw.newUTF8("RuntimeVisibleAnnotations");
+            size += 8 + anns.getSize();
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            cw.newUTF8("RuntimeInvisibleAnnotations");
+            size += 8 + ianns.getSize();
+        }
+        if (attrs != null) {
+            size += attrs.getSize(cw, null, 0, -1, -1);
+        }
+        return size;
+    }
+
+    /**
+     * Puts the content of this field into the given byte vector.
+     *
+     * @param out where the content of this field must be put.
+     */
+    void put(final ByteVector out) {
+        int mask = Opcodes.ACC_DEPRECATED
+                | ClassWriter.ACC_SYNTHETIC_ATTRIBUTE
+                | ((access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) / (ClassWriter.ACC_SYNTHETIC_ATTRIBUTE / Opcodes.ACC_SYNTHETIC));
+        out.putShort(access & ~mask).putShort(name).putShort(desc);
+        int attributeCount = 0;
+        if (value != 0) {
+            ++attributeCount;
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((cw.version & 0xFFFF) < Opcodes.V1_5 || (access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            ++attributeCount;
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            ++attributeCount;
+        }
+        if (ClassReader.SIGNATURES && signature != 0) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            ++attributeCount;
+        }
+        if (attrs != null) {
+            attributeCount += attrs.getCount();
+        }
+        out.putShort(attributeCount);
+        if (value != 0) {
+            out.putShort(cw.newUTF8("ConstantValue"));
+            out.putInt(2).putShort(value);
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((cw.version & 0xFFFF) < Opcodes.V1_5 || (access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            out.putShort(cw.newUTF8("Synthetic")).putInt(0);
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            out.putShort(cw.newUTF8("Deprecated")).putInt(0);
+        }
+        if (ClassReader.SIGNATURES && signature != 0) {
+            out.putShort(cw.newUTF8("Signature"));
+            out.putInt(2).putShort(signature);
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            out.putShort(cw.newUTF8("RuntimeVisibleAnnotations"));
+            anns.put(out);
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            out.putShort(cw.newUTF8("RuntimeInvisibleAnnotations"));
+            ianns.put(out);
+        }
+        if (attrs != null) {
+            attrs.put(cw, null, 0, -1, -1, out);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Frame.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1464 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * Information about the input and output stack map frames of a basic block.
+ *
+ * @author Eric Bruneton
+ */
+final class Frame {
+
+    /*
+     * Frames are computed in a two steps process: during the visit of each
+     * instruction, the state of the frame at the end of current basic block is
+     * updated by simulating the action of the instruction on the previous state
+     * of this so called "output frame". In visitMaxs, a fix point algorithm is
+     * used to compute the "input frame" of each basic block, i.e. the stack map
+     * frame at the beginning of the basic block, starting from the input frame
+     * of the first basic block (which is computed from the method descriptor),
+     * and by using the previously computed output frames to compute the input
+     * state of the other blocks.
+     *
+     * All output and input frames are stored as arrays of integers. Reference
+     * and array types are represented by an index into a type table (which is
+     * not the same as the constant pool of the class, in order to avoid adding
+     * unnecessary constants in the pool - not all computed frames will end up
+     * being stored in the stack map table). This allows very fast type
+     * comparisons.
+     *
+     * Output stack map frames are computed relatively to the input frame of the
+     * basic block, which is not yet known when output frames are computed. It
+     * is therefore necessary to be able to represent abstract types such as
+     * "the type at position x in the input frame locals" or "the type at
+     * position x from the top of the input frame stack" or even "the type at
+     * position x in the input frame, with y more (or less) array dimensions".
+     * This explains the rather complicated type format used in output frames.
+     *
+     * This format is the following: DIM KIND VALUE (4, 4 and 24 bits). DIM is a
+     * signed number of array dimensions (from -8 to 7). KIND is either BASE,
+     * LOCAL or STACK. BASE is used for types that are not relative to the input
+     * frame. LOCAL is used for types that are relative to the input local
+     * variable types. STACK is used for types that are relative to the input
+     * stack types. VALUE depends on KIND. For LOCAL types, it is an index in
+     * the input local variable types. For STACK types, it is a position
+     * relatively to the top of input frame stack. For BASE types, it is either
+     * one of the constants defined in FrameVisitor, or for OBJECT and
+     * UNINITIALIZED types, a tag and an index in the type table.
+     *
+     * Output frames can contain types of any kind and with a positive or
+     * negative dimension (and even unassigned types, represented by 0 - which
+     * does not correspond to any valid type value). Input frames can only
+     * contain BASE types of positive or null dimension. In all cases the type
+     * table contains only internal type names (array type descriptors are
+     * forbidden - dimensions must be represented through the DIM field).
+     *
+     * The LONG and DOUBLE types are always represented by using two slots (LONG +
+     * TOP or DOUBLE + TOP), for local variable types as well as in the operand
+     * stack. This is necessary to be able to simulate DUPx_y instructions,
+     * whose effect would be dependent on the actual type values if types were
+     * always represented by a single slot in the stack (and this is not
+     * possible, since actual type values are not always known - cf LOCAL and
+     * STACK type kinds).
+     */
+
+    /**
+     * Mask to get the dimension of a frame type. This dimension is a signed
+     * integer between -8 and 7.
+     */
+    static final int DIM = 0xF0000000;
+
+    /**
+     * Constant to be added to a type to get a type with one more dimension.
+     */
+    static final int ARRAY_OF = 0x10000000;
+
+    /**
+     * Constant to be added to a type to get a type with one less dimension.
+     */
+    static final int ELEMENT_OF = 0xF0000000;
+
+    /**
+     * Mask to get the kind of a frame type.
+     *
+     * @see #BASE
+     * @see #LOCAL
+     * @see #STACK
+     */
+    static final int KIND = 0xF000000;
+
+    /**
+     * Flag used for LOCAL and STACK types. Indicates that if this type happens
+     * to be a long or double type (during the computations of input frames),
+     * then it must be set to TOP because the second word of this value has
+     * been reused to store other data in the basic block. Hence the first word
+     * no longer stores a valid long or double value.
+     */
+    static final int TOP_IF_LONG_OR_DOUBLE = 0x800000;
+
+    /**
+     * Mask to get the value of a frame type.
+     */
+    static final int VALUE = 0x7FFFFF;
+
+    /**
+     * Mask to get the kind of base types.
+     */
+    static final int BASE_KIND = 0xFF00000;
+
+    /**
+     * Mask to get the value of base types.
+     */
+    static final int BASE_VALUE = 0xFFFFF;
+
+    /**
+     * Kind of the types that are not relative to an input stack map frame.
+     */
+    static final int BASE = 0x1000000;
+
+    /**
+     * Base kind of the base reference types. The BASE_VALUE of such types is an
+     * index into the type table.
+     */
+    static final int OBJECT = BASE | 0x700000;
+
+    /**
+     * Base kind of the uninitialized base types. The BASE_VALUE of such types
+     * in an index into the type table (the Item at that index contains both an
+     * instruction offset and an internal class name).
+     */
+    static final int UNINITIALIZED = BASE | 0x800000;
+
+    /**
+     * Kind of the types that are relative to the local variable types of an
+     * input stack map frame. The value of such types is a local variable index.
+     */
+    private static final int LOCAL = 0x2000000;
+
+    /**
+     * Kind of the the types that are relative to the stack of an input stack
+     * map frame. The value of such types is a position relatively to the top of
+     * this stack.
+     */
+    private static final int STACK = 0x3000000;
+
+    /**
+     * The TOP type. This is a BASE type.
+     */
+    static final int TOP = BASE | 0;
+
+    /**
+     * The BOOLEAN type. This is a BASE type mainly used for array types.
+     */
+    static final int BOOLEAN = BASE | 9;
+
+    /**
+     * The BYTE type. This is a BASE type mainly used for array types.
+     */
+    static final int BYTE = BASE | 10;
+
+    /**
+     * The CHAR type. This is a BASE type mainly used for array types.
+     */
+    static final int CHAR = BASE | 11;
+
+    /**
+     * The SHORT type. This is a BASE type mainly used for array types.
+     */
+    static final int SHORT = BASE | 12;
+
+    /**
+     * The INTEGER type. This is a BASE type.
+     */
+    static final int INTEGER = BASE | 1;
+
+    /**
+     * The FLOAT type. This is a BASE type.
+     */
+    static final int FLOAT = BASE | 2;
+
+    /**
+     * The DOUBLE type. This is a BASE type.
+     */
+    static final int DOUBLE = BASE | 3;
+
+    /**
+     * The LONG type. This is a BASE type.
+     */
+    static final int LONG = BASE | 4;
+
+    /**
+     * The NULL type. This is a BASE type.
+     */
+    static final int NULL = BASE | 5;
+
+    /**
+     * The UNINITIALIZED_THIS type. This is a BASE type.
+     */
+    static final int UNINITIALIZED_THIS = BASE | 6;
+
+    /**
+     * The stack size variation corresponding to each JVM instruction. This
+     * stack variation is equal to the size of the values produced by an
+     * instruction, minus the size of the values consumed by this instruction.
+     */
+    static final int[] SIZE;
+
+    /**
+     * Computes the stack size variation corresponding to each JVM instruction.
+     */
+    static {
+        int i;
+        int[] b = new int[202];
+        String s = "EFFFFFFFFGGFFFGGFFFEEFGFGFEEEEEEEEEEEEEEEEEEEEDEDEDDDDD"
+                + "CDCDEEEEEEEEEEEEEEEEEEEEBABABBBBDCFFFGGGEDCDCDCDCDCDCDCDCD"
+                + "CDCEEEEDDDDDDDCDCDCEFEFDDEEFFDEDEEEBDDBBDDDDDDCCCCCCCCEFED"
+                + "DDCDCDEEEEEEEEEEFEEEEEEDDEEDDEE";
+        for (i = 0; i < b.length; ++i) {
+            b[i] = s.charAt(i) - 'E';
+        }
+        SIZE = b;
+
+        // code to generate the above string
+        //
+        // int NA = 0; // not applicable (unused opcode or variable size opcode)
+        //
+        // b = new int[] {
+        // 0, //NOP, // visitInsn
+        // 1, //ACONST_NULL, // -
+        // 1, //ICONST_M1, // -
+        // 1, //ICONST_0, // -
+        // 1, //ICONST_1, // -
+        // 1, //ICONST_2, // -
+        // 1, //ICONST_3, // -
+        // 1, //ICONST_4, // -
+        // 1, //ICONST_5, // -
+        // 2, //LCONST_0, // -
+        // 2, //LCONST_1, // -
+        // 1, //FCONST_0, // -
+        // 1, //FCONST_1, // -
+        // 1, //FCONST_2, // -
+        // 2, //DCONST_0, // -
+        // 2, //DCONST_1, // -
+        // 1, //BIPUSH, // visitIntInsn
+        // 1, //SIPUSH, // -
+        // 1, //LDC, // visitLdcInsn
+        // NA, //LDC_W, // -
+        // NA, //LDC2_W, // -
+        // 1, //ILOAD, // visitVarInsn
+        // 2, //LLOAD, // -
+        // 1, //FLOAD, // -
+        // 2, //DLOAD, // -
+        // 1, //ALOAD, // -
+        // NA, //ILOAD_0, // -
+        // NA, //ILOAD_1, // -
+        // NA, //ILOAD_2, // -
+        // NA, //ILOAD_3, // -
+        // NA, //LLOAD_0, // -
+        // NA, //LLOAD_1, // -
+        // NA, //LLOAD_2, // -
+        // NA, //LLOAD_3, // -
+        // NA, //FLOAD_0, // -
+        // NA, //FLOAD_1, // -
+        // NA, //FLOAD_2, // -
+        // NA, //FLOAD_3, // -
+        // NA, //DLOAD_0, // -
+        // NA, //DLOAD_1, // -
+        // NA, //DLOAD_2, // -
+        // NA, //DLOAD_3, // -
+        // NA, //ALOAD_0, // -
+        // NA, //ALOAD_1, // -
+        // NA, //ALOAD_2, // -
+        // NA, //ALOAD_3, // -
+        // -1, //IALOAD, // visitInsn
+        // 0, //LALOAD, // -
+        // -1, //FALOAD, // -
+        // 0, //DALOAD, // -
+        // -1, //AALOAD, // -
+        // -1, //BALOAD, // -
+        // -1, //CALOAD, // -
+        // -1, //SALOAD, // -
+        // -1, //ISTORE, // visitVarInsn
+        // -2, //LSTORE, // -
+        // -1, //FSTORE, // -
+        // -2, //DSTORE, // -
+        // -1, //ASTORE, // -
+        // NA, //ISTORE_0, // -
+        // NA, //ISTORE_1, // -
+        // NA, //ISTORE_2, // -
+        // NA, //ISTORE_3, // -
+        // NA, //LSTORE_0, // -
+        // NA, //LSTORE_1, // -
+        // NA, //LSTORE_2, // -
+        // NA, //LSTORE_3, // -
+        // NA, //FSTORE_0, // -
+        // NA, //FSTORE_1, // -
+        // NA, //FSTORE_2, // -
+        // NA, //FSTORE_3, // -
+        // NA, //DSTORE_0, // -
+        // NA, //DSTORE_1, // -
+        // NA, //DSTORE_2, // -
+        // NA, //DSTORE_3, // -
+        // NA, //ASTORE_0, // -
+        // NA, //ASTORE_1, // -
+        // NA, //ASTORE_2, // -
+        // NA, //ASTORE_3, // -
+        // -3, //IASTORE, // visitInsn
+        // -4, //LASTORE, // -
+        // -3, //FASTORE, // -
+        // -4, //DASTORE, // -
+        // -3, //AASTORE, // -
+        // -3, //BASTORE, // -
+        // -3, //CASTORE, // -
+        // -3, //SASTORE, // -
+        // -1, //POP, // -
+        // -2, //POP2, // -
+        // 1, //DUP, // -
+        // 1, //DUP_X1, // -
+        // 1, //DUP_X2, // -
+        // 2, //DUP2, // -
+        // 2, //DUP2_X1, // -
+        // 2, //DUP2_X2, // -
+        // 0, //SWAP, // -
+        // -1, //IADD, // -
+        // -2, //LADD, // -
+        // -1, //FADD, // -
+        // -2, //DADD, // -
+        // -1, //ISUB, // -
+        // -2, //LSUB, // -
+        // -1, //FSUB, // -
+        // -2, //DSUB, // -
+        // -1, //IMUL, // -
+        // -2, //LMUL, // -
+        // -1, //FMUL, // -
+        // -2, //DMUL, // -
+        // -1, //IDIV, // -
+        // -2, //LDIV, // -
+        // -1, //FDIV, // -
+        // -2, //DDIV, // -
+        // -1, //IREM, // -
+        // -2, //LREM, // -
+        // -1, //FREM, // -
+        // -2, //DREM, // -
+        // 0, //INEG, // -
+        // 0, //LNEG, // -
+        // 0, //FNEG, // -
+        // 0, //DNEG, // -
+        // -1, //ISHL, // -
+        // -1, //LSHL, // -
+        // -1, //ISHR, // -
+        // -1, //LSHR, // -
+        // -1, //IUSHR, // -
+        // -1, //LUSHR, // -
+        // -1, //IAND, // -
+        // -2, //LAND, // -
+        // -1, //IOR, // -
+        // -2, //LOR, // -
+        // -1, //IXOR, // -
+        // -2, //LXOR, // -
+        // 0, //IINC, // visitIincInsn
+        // 1, //I2L, // visitInsn
+        // 0, //I2F, // -
+        // 1, //I2D, // -
+        // -1, //L2I, // -
+        // -1, //L2F, // -
+        // 0, //L2D, // -
+        // 0, //F2I, // -
+        // 1, //F2L, // -
+        // 1, //F2D, // -
+        // -1, //D2I, // -
+        // 0, //D2L, // -
+        // -1, //D2F, // -
+        // 0, //I2B, // -
+        // 0, //I2C, // -
+        // 0, //I2S, // -
+        // -3, //LCMP, // -
+        // -1, //FCMPL, // -
+        // -1, //FCMPG, // -
+        // -3, //DCMPL, // -
+        // -3, //DCMPG, // -
+        // -1, //IFEQ, // visitJumpInsn
+        // -1, //IFNE, // -
+        // -1, //IFLT, // -
+        // -1, //IFGE, // -
+        // -1, //IFGT, // -
+        // -1, //IFLE, // -
+        // -2, //IF_ICMPEQ, // -
+        // -2, //IF_ICMPNE, // -
+        // -2, //IF_ICMPLT, // -
+        // -2, //IF_ICMPGE, // -
+        // -2, //IF_ICMPGT, // -
+        // -2, //IF_ICMPLE, // -
+        // -2, //IF_ACMPEQ, // -
+        // -2, //IF_ACMPNE, // -
+        // 0, //GOTO, // -
+        // 1, //JSR, // -
+        // 0, //RET, // visitVarInsn
+        // -1, //TABLESWITCH, // visiTableSwitchInsn
+        // -1, //LOOKUPSWITCH, // visitLookupSwitch
+        // -1, //IRETURN, // visitInsn
+        // -2, //LRETURN, // -
+        // -1, //FRETURN, // -
+        // -2, //DRETURN, // -
+        // -1, //ARETURN, // -
+        // 0, //RETURN, // -
+        // NA, //GETSTATIC, // visitFieldInsn
+        // NA, //PUTSTATIC, // -
+        // NA, //GETFIELD, // -
+        // NA, //PUTFIELD, // -
+        // NA, //INVOKEVIRTUAL, // visitMethodInsn
+        // NA, //INVOKESPECIAL, // -
+        // NA, //INVOKESTATIC, // -
+        // NA, //INVOKEINTERFACE, // -
+        // NA, //INVOKEDYNAMIC, // visitInvokeDynamicInsn
+        // 1, //NEW, // visitTypeInsn
+        // 0, //NEWARRAY, // visitIntInsn
+        // 0, //ANEWARRAY, // visitTypeInsn
+        // 0, //ARRAYLENGTH, // visitInsn
+        // NA, //ATHROW, // -
+        // 0, //CHECKCAST, // visitTypeInsn
+        // 0, //INSTANCEOF, // -
+        // -1, //MONITORENTER, // visitInsn
+        // -1, //MONITOREXIT, // -
+        // NA, //WIDE, // NOT VISITED
+        // NA, //MULTIANEWARRAY, // visitMultiANewArrayInsn
+        // -1, //IFNULL, // visitJumpInsn
+        // -1, //IFNONNULL, // -
+        // NA, //GOTO_W, // -
+        // NA, //JSR_W, // -
+        // };
+        // for (i = 0; i < b.length; ++i) {
+        // System.err.print((char)('E' + b[i]));
+        // }
+        // System.err.println();
+    }
+
+    /**
+     * The label (i.e. basic block) to which these input and output stack map
+     * frames correspond.
+     */
+    Label owner;
+
+    /**
+     * The input stack map frame locals.
+     */
+    int[] inputLocals;
+
+    /**
+     * The input stack map frame stack.
+     */
+    int[] inputStack;
+
+    /**
+     * The output stack map frame locals.
+     */
+    private int[] outputLocals;
+
+    /**
+     * The output stack map frame stack.
+     */
+    private int[] outputStack;
+
+    /**
+     * Relative size of the output stack. The exact semantics of this field
+     * depends on the algorithm that is used.
+     *
+     * When only the maximum stack size is computed, this field is the size of
+     * the output stack relatively to the top of the input stack.
+     *
+     * When the stack map frames are completely computed, this field is the
+     * actual number of types in {@link #outputStack}.
+     */
+    private int outputStackTop;
+
+    /**
+     * Number of types that are initialized in the basic block.
+     *
+     * @see #initializations
+     */
+    private int initializationCount;
+
+    /**
+     * The types that are initialized in the basic block. A constructor
+     * invocation on an UNINITIALIZED or UNINITIALIZED_THIS type must replace
+     * <i>every occurence</i> of this type in the local variables and in the
+     * operand stack. This cannot be done during the first phase of the
+     * algorithm since, during this phase, the local variables and the operand
+     * stack are not completely computed. It is therefore necessary to store the
+     * types on which constructors are invoked in the basic block, in order to
+     * do this replacement during the second phase of the algorithm, where the
+     * frames are fully computed. Note that this array can contain types that
+     * are relative to input locals or to the input stack (see below for the
+     * description of the algorithm).
+     */
+    private int[] initializations;
+
+    /**
+     * Returns the output frame local variable type at the given index.
+     *
+     * @param local the index of the local that must be returned.
+     * @return the output frame local variable type at the given index.
+     */
+    private int get(final int local) {
+        if (outputLocals == null || local >= outputLocals.length) {
+            // this local has never been assigned in this basic block,
+            // so it is still equal to its value in the input frame
+            return LOCAL | local;
+        } else {
+            int type = outputLocals[local];
+            if (type == 0) {
+                // this local has never been assigned in this basic block,
+                // so it is still equal to its value in the input frame
+                type = outputLocals[local] = LOCAL | local;
+            }
+            return type;
+        }
+    }
+
+    /**
+     * Sets the output frame local variable type at the given index.
+     *
+     * @param local the index of the local that must be set.
+     * @param type the value of the local that must be set.
+     */
+    private void set(final int local, final int type) {
+        // creates and/or resizes the output local variables array if necessary
+        if (outputLocals == null) {
+            outputLocals = new int[10];
+        }
+        int n = outputLocals.length;
+        if (local >= n) {
+            int[] t = new int[Math.max(local + 1, 2 * n)];
+            System.arraycopy(outputLocals, 0, t, 0, n);
+            outputLocals = t;
+        }
+        // sets the local variable
+        outputLocals[local] = type;
+    }
+
+    /**
+     * Pushes a new type onto the output frame stack.
+     *
+     * @param type the type that must be pushed.
+     */
+    private void push(final int type) {
+        // creates and/or resizes the output stack array if necessary
+        if (outputStack == null) {
+            outputStack = new int[10];
+        }
+        int n = outputStack.length;
+        if (outputStackTop >= n) {
+            int[] t = new int[Math.max(outputStackTop + 1, 2 * n)];
+            System.arraycopy(outputStack, 0, t, 0, n);
+            outputStack = t;
+        }
+        // pushes the type on the output stack
+        outputStack[outputStackTop++] = type;
+        // updates the maximun height reached by the output stack, if needed
+        int top = owner.inputStackTop + outputStackTop;
+        if (top > owner.outputStackMax) {
+            owner.outputStackMax = top;
+        }
+    }
+
+    /**
+     * Pushes a new type onto the output frame stack.
+     *
+     * @param cw the ClassWriter to which this label belongs.
+     * @param desc the descriptor of the type to be pushed. Can also be a method
+     *        descriptor (in this case this method pushes its return type onto
+     *        the output frame stack).
+     */
+    private void push(final ClassWriter cw, final String desc) {
+        int type = type(cw, desc);
+        if (type != 0) {
+            push(type);
+            if (type == LONG || type == DOUBLE) {
+                push(TOP);
+            }
+        }
+    }
+
+    /**
+     * Returns the int encoding of the given type.
+     *
+     * @param cw the ClassWriter to which this label belongs.
+     * @param desc a type descriptor.
+     * @return the int encoding of the given type.
+     */
+    private static int type(final ClassWriter cw, final String desc) {
+        String t;
+        int index = desc.charAt(0) == '(' ? desc.indexOf(')') + 1 : 0;
+        switch (desc.charAt(index)) {
+            case 'V':
+                return 0;
+            case 'Z':
+            case 'C':
+            case 'B':
+            case 'S':
+            case 'I':
+                return INTEGER;
+            case 'F':
+                return FLOAT;
+            case 'J':
+                return LONG;
+            case 'D':
+                return DOUBLE;
+            case 'L':
+                // stores the internal name, not the descriptor!
+                t = desc.substring(index + 1, desc.length() - 1);
+                return OBJECT | cw.addType(t);
+                // case '[':
+            default:
+                // extracts the dimensions and the element type
+                int data;
+                int dims = index + 1;
+                while (desc.charAt(dims) == '[') {
+                    ++dims;
+                }
+                switch (desc.charAt(dims)) {
+                    case 'Z':
+                        data = BOOLEAN;
+                        break;
+                    case 'C':
+                        data = CHAR;
+                        break;
+                    case 'B':
+                        data = BYTE;
+                        break;
+                    case 'S':
+                        data = SHORT;
+                        break;
+                    case 'I':
+                        data = INTEGER;
+                        break;
+                    case 'F':
+                        data = FLOAT;
+                        break;
+                    case 'J':
+                        data = LONG;
+                        break;
+                    case 'D':
+                        data = DOUBLE;
+                        break;
+                    // case 'L':
+                    default:
+                        // stores the internal name, not the descriptor
+                        t = desc.substring(dims + 1, desc.length() - 1);
+                        data = OBJECT | cw.addType(t);
+                }
+                return (dims - index) << 28 | data;
+        }
+    }
+
+    /**
+     * Pops a type from the output frame stack and returns its value.
+     *
+     * @return the type that has been popped from the output frame stack.
+     */
+    private int pop() {
+        if (outputStackTop > 0) {
+            return outputStack[--outputStackTop];
+        } else {
+            // if the output frame stack is empty, pops from the input stack
+            return STACK | -(--owner.inputStackTop);
+        }
+    }
+
+    /**
+     * Pops the given number of types from the output frame stack.
+     *
+     * @param elements the number of types that must be popped.
+     */
+    private void pop(final int elements) {
+        if (outputStackTop >= elements) {
+            outputStackTop -= elements;
+        } else {
+            // if the number of elements to be popped is greater than the number
+            // of elements in the output stack, clear it, and pops the remaining
+            // elements from the input stack.
+            owner.inputStackTop -= elements - outputStackTop;
+            outputStackTop = 0;
+        }
+    }
+
+    /**
+     * Pops a type from the output frame stack.
+     *
+     * @param desc the descriptor of the type to be popped. Can also be a method
+     *        descriptor (in this case this method pops the types corresponding
+     *        to the method arguments).
+     */
+    private void pop(final String desc) {
+        char c = desc.charAt(0);
+        if (c == '(') {
+            pop((Type.getArgumentsAndReturnSizes(desc) >> 2) - 1);
+        } else if (c == 'J' || c == 'D') {
+            pop(2);
+        } else {
+            pop(1);
+        }
+    }
+
+    /**
+     * Adds a new type to the list of types on which a constructor is invoked in
+     * the basic block.
+     *
+     * @param var a type on a which a constructor is invoked.
+     */
+    private void init(final int var) {
+        // creates and/or resizes the initializations array if necessary
+        if (initializations == null) {
+            initializations = new int[2];
+        }
+        int n = initializations.length;
+        if (initializationCount >= n) {
+            int[] t = new int[Math.max(initializationCount + 1, 2 * n)];
+            System.arraycopy(initializations, 0, t, 0, n);
+            initializations = t;
+        }
+        // stores the type to be initialized
+        initializations[initializationCount++] = var;
+    }
+
+    /**
+     * Replaces the given type with the appropriate type if it is one of the
+     * types on which a constructor is invoked in the basic block.
+     *
+     * @param cw the ClassWriter to which this label belongs.
+     * @param t a type
+     * @return t or, if t is one of the types on which a constructor is invoked
+     *         in the basic block, the type corresponding to this constructor.
+     */
+    private int init(final ClassWriter cw, final int t) {
+        int s;
+        if (t == UNINITIALIZED_THIS) {
+            s = OBJECT | cw.addType(cw.thisName);
+        } else if ((t & (DIM | BASE_KIND)) == UNINITIALIZED) {
+            String type = cw.typeTable[t & BASE_VALUE].strVal1;
+            s = OBJECT | cw.addType(type);
+        } else {
+            return t;
+        }
+        for (int j = 0; j < initializationCount; ++j) {
+            int u = initializations[j];
+            int dim = u & DIM;
+            int kind = u & KIND;
+            if (kind == LOCAL) {
+                u = dim + inputLocals[u & VALUE];
+            } else if (kind == STACK) {
+                u = dim + inputStack[inputStack.length - (u & VALUE)];
+            }
+            if (t == u) {
+                return s;
+            }
+        }
+        return t;
+    }
+
+    /**
+     * Initializes the input frame of the first basic block from the method
+     * descriptor.
+     *
+     * @param cw the ClassWriter to which this label belongs.
+     * @param access the access flags of the method to which this label belongs.
+     * @param args the formal parameter types of this method.
+     * @param maxLocals the maximum number of local variables of this method.
+     */
+    void initInputFrame(
+        final ClassWriter cw,
+        final int access,
+        final Type[] args,
+        final int maxLocals)
+    {
+        inputLocals = new int[maxLocals];
+        inputStack = new int[0];
+        int i = 0;
+        if ((access & Opcodes.ACC_STATIC) == 0) {
+            if ((access & MethodWriter.ACC_CONSTRUCTOR) == 0) {
+                inputLocals[i++] = OBJECT | cw.addType(cw.thisName);
+            } else {
+                inputLocals[i++] = UNINITIALIZED_THIS;
+            }
+        }
+        for (int j = 0; j < args.length; ++j) {
+            int t = type(cw, args[j].getDescriptor());
+            inputLocals[i++] = t;
+            if (t == LONG || t == DOUBLE) {
+                inputLocals[i++] = TOP;
+            }
+        }
+        while (i < maxLocals) {
+            inputLocals[i++] = TOP;
+        }
+    }
+
+    /**
+     * Simulates the action of the given instruction on the output stack frame.
+     *
+     * @param opcode the opcode of the instruction.
+     * @param arg the operand of the instruction, if any.
+     * @param cw the class writer to which this label belongs.
+     * @param item the operand of the instructions, if any.
+     */
+    void execute(
+        final int opcode,
+        final int arg,
+        final ClassWriter cw,
+        final Item item)
+    {
+        int t1, t2, t3, t4;
+        switch (opcode) {
+            case Opcodes.NOP:
+            case Opcodes.INEG:
+            case Opcodes.LNEG:
+            case Opcodes.FNEG:
+            case Opcodes.DNEG:
+            case Opcodes.I2B:
+            case Opcodes.I2C:
+            case Opcodes.I2S:
+            case Opcodes.GOTO:
+            case Opcodes.RETURN:
+                break;
+            case Opcodes.ACONST_NULL:
+                push(NULL);
+                break;
+            case Opcodes.ICONST_M1:
+            case Opcodes.ICONST_0:
+            case Opcodes.ICONST_1:
+            case Opcodes.ICONST_2:
+            case Opcodes.ICONST_3:
+            case Opcodes.ICONST_4:
+            case Opcodes.ICONST_5:
+            case Opcodes.BIPUSH:
+            case Opcodes.SIPUSH:
+            case Opcodes.ILOAD:
+                push(INTEGER);
+                break;
+            case Opcodes.LCONST_0:
+            case Opcodes.LCONST_1:
+            case Opcodes.LLOAD:
+                push(LONG);
+                push(TOP);
+                break;
+            case Opcodes.FCONST_0:
+            case Opcodes.FCONST_1:
+            case Opcodes.FCONST_2:
+            case Opcodes.FLOAD:
+                push(FLOAT);
+                break;
+            case Opcodes.DCONST_0:
+            case Opcodes.DCONST_1:
+            case Opcodes.DLOAD:
+                push(DOUBLE);
+                push(TOP);
+                break;
+            case Opcodes.LDC:
+                switch (item.type) {
+                    case ClassWriter.INT:
+                        push(INTEGER);
+                        break;
+                    case ClassWriter.LONG:
+                        push(LONG);
+                        push(TOP);
+                        break;
+                    case ClassWriter.FLOAT:
+                        push(FLOAT);
+                        break;
+                    case ClassWriter.DOUBLE:
+                        push(DOUBLE);
+                        push(TOP);
+                        break;
+                    case ClassWriter.CLASS:
+                        push(OBJECT | cw.addType("java/lang/Class"));
+                        break;
+                    case ClassWriter.STR:
+                        push(OBJECT | cw.addType("java/lang/String"));
+                        break;
+                    case ClassWriter.MTYPE:
+                        push(OBJECT | cw.addType("java/lang/invoke/MethodType"));
+                        break;
+                    // case ClassWriter.HANDLE_BASE + [1..9]:
+                    default:
+                        push(OBJECT | cw.addType("java/lang/invoke/MethodHandle"));
+                }
+                break;
+            case Opcodes.ALOAD:
+                push(get(arg));
+                break;
+            case Opcodes.IALOAD:
+            case Opcodes.BALOAD:
+            case Opcodes.CALOAD:
+            case Opcodes.SALOAD:
+                pop(2);
+                push(INTEGER);
+                break;
+            case Opcodes.LALOAD:
+            case Opcodes.D2L:
+                pop(2);
+                push(LONG);
+                push(TOP);
+                break;
+            case Opcodes.FALOAD:
+                pop(2);
+                push(FLOAT);
+                break;
+            case Opcodes.DALOAD:
+            case Opcodes.L2D:
+                pop(2);
+                push(DOUBLE);
+                push(TOP);
+                break;
+            case Opcodes.AALOAD:
+                pop(1);
+                t1 = pop();
+                push(ELEMENT_OF + t1);
+                break;
+            case Opcodes.ISTORE:
+            case Opcodes.FSTORE:
+            case Opcodes.ASTORE:
+                t1 = pop();
+                set(arg, t1);
+                if (arg > 0) {
+                    t2 = get(arg - 1);
+                    // if t2 is of kind STACK or LOCAL we cannot know its size!
+                    if (t2 == LONG || t2 == DOUBLE) {
+                        set(arg - 1, TOP);
+                    } else if ((t2 & KIND) != BASE) {
+                        set(arg - 1, t2 | TOP_IF_LONG_OR_DOUBLE);
+                    }
+                }
+                break;
+            case Opcodes.LSTORE:
+            case Opcodes.DSTORE:
+                pop(1);
+                t1 = pop();
+                set(arg, t1);
+                set(arg + 1, TOP);
+                if (arg > 0) {
+                    t2 = get(arg - 1);
+                    // if t2 is of kind STACK or LOCAL we cannot know its size!
+                    if (t2 == LONG || t2 == DOUBLE) {
+                        set(arg - 1, TOP);
+                    } else if ((t2 & KIND) != BASE) {
+                        set(arg - 1, t2 | TOP_IF_LONG_OR_DOUBLE);
+                    }
+                }
+                break;
+            case Opcodes.IASTORE:
+            case Opcodes.BASTORE:
+            case Opcodes.CASTORE:
+            case Opcodes.SASTORE:
+            case Opcodes.FASTORE:
+            case Opcodes.AASTORE:
+                pop(3);
+                break;
+            case Opcodes.LASTORE:
+            case Opcodes.DASTORE:
+                pop(4);
+                break;
+            case Opcodes.POP:
+            case Opcodes.IFEQ:
+            case Opcodes.IFNE:
+            case Opcodes.IFLT:
+            case Opcodes.IFGE:
+            case Opcodes.IFGT:
+            case Opcodes.IFLE:
+            case Opcodes.IRETURN:
+            case Opcodes.FRETURN:
+            case Opcodes.ARETURN:
+            case Opcodes.TABLESWITCH:
+            case Opcodes.LOOKUPSWITCH:
+            case Opcodes.ATHROW:
+            case Opcodes.MONITORENTER:
+            case Opcodes.MONITOREXIT:
+            case Opcodes.IFNULL:
+            case Opcodes.IFNONNULL:
+                pop(1);
+                break;
+            case Opcodes.POP2:
+            case Opcodes.IF_ICMPEQ:
+            case Opcodes.IF_ICMPNE:
+            case Opcodes.IF_ICMPLT:
+            case Opcodes.IF_ICMPGE:
+            case Opcodes.IF_ICMPGT:
+            case Opcodes.IF_ICMPLE:
+            case Opcodes.IF_ACMPEQ:
+            case Opcodes.IF_ACMPNE:
+            case Opcodes.LRETURN:
+            case Opcodes.DRETURN:
+                pop(2);
+                break;
+            case Opcodes.DUP:
+                t1 = pop();
+                push(t1);
+                push(t1);
+                break;
+            case Opcodes.DUP_X1:
+                t1 = pop();
+                t2 = pop();
+                push(t1);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP_X2:
+                t1 = pop();
+                t2 = pop();
+                t3 = pop();
+                push(t1);
+                push(t3);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP2:
+                t1 = pop();
+                t2 = pop();
+                push(t2);
+                push(t1);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP2_X1:
+                t1 = pop();
+                t2 = pop();
+                t3 = pop();
+                push(t2);
+                push(t1);
+                push(t3);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP2_X2:
+                t1 = pop();
+                t2 = pop();
+                t3 = pop();
+                t4 = pop();
+                push(t2);
+                push(t1);
+                push(t4);
+                push(t3);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.SWAP:
+                t1 = pop();
+                t2 = pop();
+                push(t1);
+                push(t2);
+                break;
+            case Opcodes.IADD:
+            case Opcodes.ISUB:
+            case Opcodes.IMUL:
+            case Opcodes.IDIV:
+            case Opcodes.IREM:
+            case Opcodes.IAND:
+            case Opcodes.IOR:
+            case Opcodes.IXOR:
+            case Opcodes.ISHL:
+            case Opcodes.ISHR:
+            case Opcodes.IUSHR:
+            case Opcodes.L2I:
+            case Opcodes.D2I:
+            case Opcodes.FCMPL:
+            case Opcodes.FCMPG:
+                pop(2);
+                push(INTEGER);
+                break;
+            case Opcodes.LADD:
+            case Opcodes.LSUB:
+            case Opcodes.LMUL:
+            case Opcodes.LDIV:
+            case Opcodes.LREM:
+            case Opcodes.LAND:
+            case Opcodes.LOR:
+            case Opcodes.LXOR:
+                pop(4);
+                push(LONG);
+                push(TOP);
+                break;
+            case Opcodes.FADD:
+            case Opcodes.FSUB:
+            case Opcodes.FMUL:
+            case Opcodes.FDIV:
+            case Opcodes.FREM:
+            case Opcodes.L2F:
+            case Opcodes.D2F:
+                pop(2);
+                push(FLOAT);
+                break;
+            case Opcodes.DADD:
+            case Opcodes.DSUB:
+            case Opcodes.DMUL:
+            case Opcodes.DDIV:
+            case Opcodes.DREM:
+                pop(4);
+                push(DOUBLE);
+                push(TOP);
+                break;
+            case Opcodes.LSHL:
+            case Opcodes.LSHR:
+            case Opcodes.LUSHR:
+                pop(3);
+                push(LONG);
+                push(TOP);
+                break;
+            case Opcodes.IINC:
+                set(arg, INTEGER);
+                break;
+            case Opcodes.I2L:
+            case Opcodes.F2L:
+                pop(1);
+                push(LONG);
+                push(TOP);
+                break;
+            case Opcodes.I2F:
+                pop(1);
+                push(FLOAT);
+                break;
+            case Opcodes.I2D:
+            case Opcodes.F2D:
+                pop(1);
+                push(DOUBLE);
+                push(TOP);
+                break;
+            case Opcodes.F2I:
+            case Opcodes.ARRAYLENGTH:
+            case Opcodes.INSTANCEOF:
+                pop(1);
+                push(INTEGER);
+                break;
+            case Opcodes.LCMP:
+            case Opcodes.DCMPL:
+            case Opcodes.DCMPG:
+                pop(4);
+                push(INTEGER);
+                break;
+            case Opcodes.JSR:
+            case Opcodes.RET:
+                throw new RuntimeException("JSR/RET are not supported with computeFrames option");
+            case Opcodes.GETSTATIC:
+                push(cw, item.strVal3);
+                break;
+            case Opcodes.PUTSTATIC:
+                pop(item.strVal3);
+                break;
+            case Opcodes.GETFIELD:
+                pop(1);
+                push(cw, item.strVal3);
+                break;
+            case Opcodes.PUTFIELD:
+                pop(item.strVal3);
+                pop();
+                break;
+            case Opcodes.INVOKEVIRTUAL:
+            case Opcodes.INVOKESPECIAL:
+            case Opcodes.INVOKESTATIC:
+            case Opcodes.INVOKEINTERFACE:
+                pop(item.strVal3);
+                if (opcode != Opcodes.INVOKESTATIC) {
+                    t1 = pop();
+                    if (opcode == Opcodes.INVOKESPECIAL
+                            && item.strVal2.charAt(0) == '<')
+                    {
+                        init(t1);
+                    }
+                }
+                push(cw, item.strVal3);
+                break;
+            case Opcodes.INVOKEDYNAMIC:
+                pop(item.strVal2);
+                push(cw, item.strVal2);
+                break;
+            case Opcodes.NEW:
+                push(UNINITIALIZED | cw.addUninitializedType(item.strVal1, arg));
+                break;
+            case Opcodes.NEWARRAY:
+                pop();
+                switch (arg) {
+                    case Opcodes.T_BOOLEAN:
+                        push(ARRAY_OF | BOOLEAN);
+                        break;
+                    case Opcodes.T_CHAR:
+                        push(ARRAY_OF | CHAR);
+                        break;
+                    case Opcodes.T_BYTE:
+                        push(ARRAY_OF | BYTE);
+                        break;
+                    case Opcodes.T_SHORT:
+                        push(ARRAY_OF | SHORT);
+                        break;
+                    case Opcodes.T_INT:
+                        push(ARRAY_OF | INTEGER);
+                        break;
+                    case Opcodes.T_FLOAT:
+                        push(ARRAY_OF | FLOAT);
+                        break;
+                    case Opcodes.T_DOUBLE:
+                        push(ARRAY_OF | DOUBLE);
+                        break;
+                    // case Opcodes.T_LONG:
+                    default:
+                        push(ARRAY_OF | LONG);
+                        break;
+                }
+                break;
+            case Opcodes.ANEWARRAY:
+                String s = item.strVal1;
+                pop();
+                if (s.charAt(0) == '[') {
+                    push(cw, '[' + s);
+                } else {
+                    push(ARRAY_OF | OBJECT | cw.addType(s));
+                }
+                break;
+            case Opcodes.CHECKCAST:
+                s = item.strVal1;
+                pop();
+                if (s.charAt(0) == '[') {
+                    push(cw, s);
+                } else {
+                    push(OBJECT | cw.addType(s));
+                }
+                break;
+            // case Opcodes.MULTIANEWARRAY:
+            default:
+                pop(arg);
+                push(cw, item.strVal1);
+                break;
+        }
+    }
+
+    /**
+     * Merges the input frame of the given basic block with the input and output
+     * frames of this basic block. Returns <tt>true</tt> if the input frame of
+     * the given label has been changed by this operation.
+     *
+     * @param cw the ClassWriter to which this label belongs.
+     * @param frame the basic block whose input frame must be updated.
+     * @param edge the kind of the {@link Edge} between this label and 'label'.
+     *        See {@link Edge#info}.
+     * @return <tt>true</tt> if the input frame of the given label has been
+     *         changed by this operation.
+     */
+    boolean merge(final ClassWriter cw, final Frame frame, final int edge) {
+        boolean changed = false;
+        int i, s, dim, kind, t;
+
+        int nLocal = inputLocals.length;
+        int nStack = inputStack.length;
+        if (frame.inputLocals == null) {
+            frame.inputLocals = new int[nLocal];
+            changed = true;
+        }
+
+        for (i = 0; i < nLocal; ++i) {
+            if (outputLocals != null && i < outputLocals.length) {
+                s = outputLocals[i];
+                if (s == 0) {
+                    t = inputLocals[i];
+                } else {
+                    dim = s & DIM;
+                    kind = s & KIND;
+                    if (kind == BASE) {
+                        t = s;
+                    } else {
+                        if (kind == LOCAL) {
+                            t = dim + inputLocals[s & VALUE];
+                        } else {
+                            t = dim + inputStack[nStack - (s & VALUE)];
+                        }
+                        if ((s & TOP_IF_LONG_OR_DOUBLE) != 0 && (t == LONG || t == DOUBLE)) {
+                            t = TOP;
+                        }
+                    }
+                }
+            } else {
+                t = inputLocals[i];
+            }
+            if (initializations != null) {
+                t = init(cw, t);
+            }
+            changed |= merge(cw, t, frame.inputLocals, i);
+        }
+
+        if (edge > 0) {
+            for (i = 0; i < nLocal; ++i) {
+                t = inputLocals[i];
+                changed |= merge(cw, t, frame.inputLocals, i);
+            }
+            if (frame.inputStack == null) {
+                frame.inputStack = new int[1];
+                changed = true;
+            }
+            changed |= merge(cw, edge, frame.inputStack, 0);
+            return changed;
+        }
+
+        int nInputStack = inputStack.length + owner.inputStackTop;
+        if (frame.inputStack == null) {
+            frame.inputStack = new int[nInputStack + outputStackTop];
+            changed = true;
+        }
+
+        for (i = 0; i < nInputStack; ++i) {
+            t = inputStack[i];
+            if (initializations != null) {
+                t = init(cw, t);
+            }
+            changed |= merge(cw, t, frame.inputStack, i);
+        }
+        for (i = 0; i < outputStackTop; ++i) {
+            s = outputStack[i];
+            dim = s & DIM;
+            kind = s & KIND;
+            if (kind == BASE) {
+                t = s;
+            } else {
+                if (kind == LOCAL) {
+                    t = dim + inputLocals[s & VALUE];
+                } else {
+                    t = dim + inputStack[nStack - (s & VALUE)];
+                }
+                if ((s & TOP_IF_LONG_OR_DOUBLE) != 0 && (t == LONG || t == DOUBLE)) {
+                    t = TOP;
+                }
+            }
+            if (initializations != null) {
+                t = init(cw, t);
+            }
+            changed |= merge(cw, t, frame.inputStack, nInputStack + i);
+        }
+        return changed;
+    }
+
+    /**
+     * Merges the type at the given index in the given type array with the given
+     * type. Returns <tt>true</tt> if the type array has been modified by this
+     * operation.
+     *
+     * @param cw the ClassWriter to which this label belongs.
+     * @param t the type with which the type array element must be merged.
+     * @param types an array of types.
+     * @param index the index of the type that must be merged in 'types'.
+     * @return <tt>true</tt> if the type array has been modified by this
+     *         operation.
+     */
+    private static boolean merge(
+        final ClassWriter cw,
+        int t,
+        final int[] types,
+        final int index)
+    {
+        int u = types[index];
+        if (u == t) {
+            // if the types are equal, merge(u,t)=u, so there is no change
+            return false;
+        }
+        if ((t & ~DIM) == NULL) {
+            if (u == NULL) {
+                return false;
+            }
+            t = NULL;
+        }
+        if (u == 0) {
+            // if types[index] has never been assigned, merge(u,t)=t
+            types[index] = t;
+            return true;
+        }
+        int v;
+        if ((u & BASE_KIND) == OBJECT || (u & DIM) != 0) {
+            // if u is a reference type of any dimension
+            if (t == NULL) {
+                // if t is the NULL type, merge(u,t)=u, so there is no change
+                return false;
+            } else if ((t & (DIM | BASE_KIND)) == (u & (DIM | BASE_KIND))) {
+                if ((u & BASE_KIND) == OBJECT) {
+                    // if t is also a reference type, and if u and t have the
+                    // same dimension merge(u,t) = dim(t) | common parent of the
+                    // element types of u and t
+                    v = (t & DIM) | OBJECT
+                            | cw.getMergedType(t & BASE_VALUE, u & BASE_VALUE);
+                } else {
+                    // if u and t are array types, but not with the same element
+                    // type, merge(u,t)=java/lang/Object
+                    v = OBJECT | cw.addType("java/lang/Object");
+                }
+            } else if ((t & BASE_KIND) == OBJECT || (t & DIM) != 0) {
+                // if t is any other reference or array type,
+                // merge(u,t)=java/lang/Object
+                v = OBJECT | cw.addType("java/lang/Object");
+            } else {
+                // if t is any other type, merge(u,t)=TOP
+                v = TOP;
+            }
+        } else if (u == NULL) {
+            // if u is the NULL type, merge(u,t)=t,
+            // or TOP if t is not a reference type
+            v = (t & BASE_KIND) == OBJECT || (t & DIM) != 0 ? t : TOP;
+        } else {
+            // if u is any other type, merge(u,t)=TOP whatever t
+            v = TOP;
+        }
+        if (u != v) {
+            types[index] = v;
+            return true;
+        }
+        return false;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Handle.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,188 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A reference to a field or a method.
+ *
+ * @author Remi Forax
+ * @author Eric Bruneton
+ */
+public final class Handle {
+
+    /**
+     * The kind of field or method designated by this Handle. Should be
+     * {@link Opcodes#H_GETFIELD}, {@link Opcodes#H_GETSTATIC},
+     * {@link Opcodes#H_PUTFIELD}, {@link Opcodes#H_PUTSTATIC},
+     * {@link Opcodes#H_INVOKEVIRTUAL}, {@link Opcodes#H_INVOKESTATIC},
+     * {@link Opcodes#H_INVOKESPECIAL}, {@link Opcodes#H_NEWINVOKESPECIAL} or
+     * {@link Opcodes#H_INVOKEINTERFACE}.
+     */
+    final int tag;
+
+    /**
+     * The internal name of the field or method designed by this handle.
+     */
+    final String owner;
+
+    /**
+     * The name of the field or method designated by this handle.
+     */
+    final String name;
+
+    /**
+     * The descriptor of the field or method designated by this handle.
+     */
+    final String desc;
+
+    /**
+     * Constructs a new field or method handle.
+     *
+     * @param tag the kind of field or method designated by this Handle. Must be
+     *        {@link Opcodes#H_GETFIELD}, {@link Opcodes#H_GETSTATIC},
+     *        {@link Opcodes#H_PUTFIELD}, {@link Opcodes#H_PUTSTATIC},
+     *        {@link Opcodes#H_INVOKEVIRTUAL}, {@link Opcodes#H_INVOKESTATIC},
+     *        {@link Opcodes#H_INVOKESPECIAL},
+     *        {@link Opcodes#H_NEWINVOKESPECIAL} or
+     *        {@link Opcodes#H_INVOKEINTERFACE}.
+     * @param owner the internal name of the field or method designed by this
+     *        handle.
+     * @param name the name of the field or method designated by this handle.
+     * @param desc the descriptor of the field or method designated by this
+     *        handle.
+     */
+    public Handle(int tag, String owner, String name, String desc) {
+        this.tag = tag;
+        this.owner = owner;
+        this.name = name;
+        this.desc = desc;
+    }
+
+    /**
+     * Returns the kind of field or method designated by this handle.
+     *
+     * @return {@link Opcodes#H_GETFIELD}, {@link Opcodes#H_GETSTATIC},
+     *         {@link Opcodes#H_PUTFIELD}, {@link Opcodes#H_PUTSTATIC},
+     *         {@link Opcodes#H_INVOKEVIRTUAL}, {@link Opcodes#H_INVOKESTATIC},
+     *         {@link Opcodes#H_INVOKESPECIAL},
+     *         {@link Opcodes#H_NEWINVOKESPECIAL} or
+     *         {@link Opcodes#H_INVOKEINTERFACE}.
+     */
+    public int getTag() {
+        return tag;
+    }
+
+    /**
+     * Returns the internal name of the field or method designed by this
+     * handle.
+     *
+     * @return the internal name of the field or method designed by this
+     *         handle.
+     */
+    public String getOwner() {
+        return owner;
+    }
+
+    /**
+     * Returns the name of the field or method designated by this handle.
+     *
+     * @return the name of the field or method designated by this handle.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Returns the descriptor of the field or method designated by this handle.
+     *
+     * @return the descriptor of the field or method designated by this handle.
+     */
+    public String getDesc() {
+        return desc;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (obj == this) {
+            return true;
+        }
+        if (!(obj instanceof Handle)) {
+            return false;
+        }
+        Handle h = (Handle) obj;
+        return tag == h.tag && owner.equals(h.owner)
+                && name.equals(h.name) && desc.equals(h.desc);
+    }
+
+    @Override
+    public int hashCode() {
+        return tag + owner.hashCode() * name.hashCode() * desc.hashCode();
+    }
+
+    /**
+     * Returns the textual representation of this handle. The textual
+     * representation is: <pre>owner '.' name desc ' ' '(' tag ')'</pre>. As
+     * this format is unambiguous, it can be parsed if necessary.
+     */
+    @Override
+    public String toString() {
+        return owner + '.' + name + desc + " (" + tag + ')';
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Handler.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,147 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * Information about an exception handler block.
+ *
+ * @author Eric Bruneton
+ */
+class Handler {
+
+    /**
+     * Beginning of the exception handler's scope (inclusive).
+     */
+    Label start;
+
+    /**
+     * End of the exception handler's scope (exclusive).
+     */
+    Label end;
+
+    /**
+     * Beginning of the exception handler's code.
+     */
+    Label handler;
+
+    /**
+     * Internal name of the type of exceptions handled by this handler, or
+     * <tt>null</tt> to catch any exceptions.
+     */
+    String desc;
+
+    /**
+     * Constant pool index of the internal name of the type of exceptions
+     * handled by this handler, or 0 to catch any exceptions.
+     */
+    int type;
+
+    /**
+     * Next exception handler block info.
+     */
+    Handler next;
+
+    /**
+     * Removes the range between start and end from the given exception
+     * handlers.
+     *
+     * @param h an exception handler list.
+     * @param start the start of the range to be removed.
+     * @param end the end of the range to be removed. Maybe null.
+     * @return the exception handler list with the start-end range removed.
+     */
+    static Handler remove(Handler h, Label start, Label end) {
+        if (h == null) {
+            return null;
+        } else {
+            h.next = remove(h.next, start, end);
+        }
+        int hstart = h.start.position;
+        int hend = h.end.position;
+        int s = start.position;
+        int e = end == null ? Integer.MAX_VALUE : end.position;
+        // if [hstart,hend[ and [s,e[ intervals intersect...
+        if (s < hend && e > hstart) {
+            if (s <= hstart) {
+                if (e >= hend) {
+                    // [hstart,hend[ fully included in [s,e[, h removed
+                    h = h.next;
+                } else {
+                    // [hstart,hend[ minus [s,e[ = [e,hend[
+                    h.start = end;
+                }
+            } else if (e >= hend) {
+                // [hstart,hend[ minus [s,e[ = [hstart,s[
+                h.end = start;
+            } else {
+                // [hstart,hend[ minus [s,e[ = [hstart,s[ + [e,hend[
+                Handler g = new Handler();
+                g.start = end;
+                g.end = h.end;
+                g.handler = h.handler;
+                g.desc = h.desc;
+                g.type = h.type;
+                g.next = h.next;
+                h.end = start;
+                h.next = g;
+            }
+        }
+        return h;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Item.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,326 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A constant pool item. Constant pool items can be created with the 'newXXX'
+ * methods in the {@link ClassWriter} class.
+ *
+ * @author Eric Bruneton
+ */
+final class Item {
+
+    /**
+     * Index of this item in the constant pool.
+     */
+    int index;
+
+    /**
+     * Type of this constant pool item. A single class is used to represent all
+     * constant pool item types, in order to minimize the bytecode size of this
+     * package. The value of this field is one of {@link ClassWriter#INT},
+     * {@link ClassWriter#LONG}, {@link ClassWriter#FLOAT},
+     * {@link ClassWriter#DOUBLE}, {@link ClassWriter#UTF8},
+     * {@link ClassWriter#STR}, {@link ClassWriter#CLASS},
+     * {@link ClassWriter#NAME_TYPE}, {@link ClassWriter#FIELD},
+     * {@link ClassWriter#METH}, {@link ClassWriter#IMETH},
+     * {@link ClassWriter#MTYPE}, {@link ClassWriter#INDY}.
+     *
+     * MethodHandle constant 9 variations are stored using a range
+     * of 9 values from {@link ClassWriter#HANDLE_BASE} + 1 to
+     * {@link ClassWriter#HANDLE_BASE} + 9.
+     *
+     * Special Item types are used for Items that are stored in the ClassWriter
+     * {@link ClassWriter#typeTable}, instead of the constant pool, in order to
+     * avoid clashes with normal constant pool items in the ClassWriter constant
+     * pool's hash table. These special item types are
+     * {@link ClassWriter#TYPE_NORMAL}, {@link ClassWriter#TYPE_UNINIT} and
+     * {@link ClassWriter#TYPE_MERGED}.
+     */
+    int type;
+
+    /**
+     * Value of this item, for an integer item.
+     */
+    int intVal;
+
+    /**
+     * Value of this item, for a long item.
+     */
+    long longVal;
+
+    /**
+     * First part of the value of this item, for items that do not hold a
+     * primitive value.
+     */
+    String strVal1;
+
+    /**
+     * Second part of the value of this item, for items that do not hold a
+     * primitive value.
+     */
+    String strVal2;
+
+    /**
+     * Third part of the value of this item, for items that do not hold a
+     * primitive value.
+     */
+    String strVal3;
+
+    /**
+     * The hash code value of this constant pool item.
+     */
+    int hashCode;
+
+    /**
+     * Link to another constant pool item, used for collision lists in the
+     * constant pool's hash table.
+     */
+    Item next;
+
+    /**
+     * Constructs an uninitialized {@link Item}.
+     */
+    Item() {
+    }
+
+    /**
+     * Constructs an uninitialized {@link Item} for constant pool element at
+     * given position.
+     *
+     * @param index index of the item to be constructed.
+     */
+    Item(final int index) {
+        this.index = index;
+    }
+
+    /**
+     * Constructs a copy of the given item.
+     *
+     * @param index index of the item to be constructed.
+     * @param i the item that must be copied into the item to be constructed.
+     */
+    Item(final int index, final Item i) {
+        this.index = index;
+        type = i.type;
+        intVal = i.intVal;
+        longVal = i.longVal;
+        strVal1 = i.strVal1;
+        strVal2 = i.strVal2;
+        strVal3 = i.strVal3;
+        hashCode = i.hashCode;
+    }
+
+    /**
+     * Sets this item to an integer item.
+     *
+     * @param intVal the value of this item.
+     */
+    void set(final int intVal) {
+        this.type = ClassWriter.INT;
+        this.intVal = intVal;
+        this.hashCode = 0x7FFFFFFF & (type + intVal);
+    }
+
+    /**
+     * Sets this item to a long item.
+     *
+     * @param longVal the value of this item.
+     */
+    void set(final long longVal) {
+        this.type = ClassWriter.LONG;
+        this.longVal = longVal;
+        this.hashCode = 0x7FFFFFFF & (type + (int) longVal);
+    }
+
+    /**
+     * Sets this item to a float item.
+     *
+     * @param floatVal the value of this item.
+     */
+    void set(final float floatVal) {
+        this.type = ClassWriter.FLOAT;
+        this.intVal = Float.floatToRawIntBits(floatVal);
+        this.hashCode = 0x7FFFFFFF & (type + (int) floatVal);
+    }
+
+    /**
+     * Sets this item to a double item.
+     *
+     * @param doubleVal the value of this item.
+     */
+    void set(final double doubleVal) {
+        this.type = ClassWriter.DOUBLE;
+        this.longVal = Double.doubleToRawLongBits(doubleVal);
+        this.hashCode = 0x7FFFFFFF & (type + (int) doubleVal);
+    }
+
+    /**
+     * Sets this item to an item that do not hold a primitive value.
+     *
+     * @param type the type of this item.
+     * @param strVal1 first part of the value of this item.
+     * @param strVal2 second part of the value of this item.
+     * @param strVal3 third part of the value of this item.
+     */
+    void set(
+        final int type,
+        final String strVal1,
+        final String strVal2,
+        final String strVal3)
+    {
+        this.type = type;
+        this.strVal1 = strVal1;
+        this.strVal2 = strVal2;
+        this.strVal3 = strVal3;
+        switch (type) {
+            case ClassWriter.UTF8:
+            case ClassWriter.STR:
+            case ClassWriter.CLASS:
+            case ClassWriter.MTYPE:
+            case ClassWriter.TYPE_NORMAL:
+                hashCode = 0x7FFFFFFF & (type + strVal1.hashCode());
+                return;
+            case ClassWriter.NAME_TYPE:
+                hashCode = 0x7FFFFFFF & (type + strVal1.hashCode()
+                        * strVal2.hashCode());
+                return;
+                // ClassWriter.FIELD:
+                // ClassWriter.METH:
+                // ClassWriter.IMETH:
+                // ClassWriter.HANDLE_BASE + 1..9
+            default:
+                hashCode = 0x7FFFFFFF & (type + strVal1.hashCode()
+                        * strVal2.hashCode() * strVal3.hashCode());
+        }
+    }
+
+    /**
+     * Sets the item to an InvokeDynamic item.
+     *
+     * @param name invokedynamic's name.
+     * @param desc invokedynamic's desc.
+     * @param bsmIndex zero based index into the class attribute BootrapMethods.
+     */
+    void set(String name, String desc, int bsmIndex) {
+        this.type = ClassWriter.INDY;
+        this.longVal = bsmIndex;
+        this.strVal1 = name;
+        this.strVal2 = desc;
+        this.hashCode = 0x7FFFFFFF & (ClassWriter.INDY + bsmIndex
+                * strVal1.hashCode() * strVal2.hashCode());
+    }
+
+    /**
+     * Sets the item to a BootstrapMethod item.
+     *
+     * @param position position in byte in the class attribute BootrapMethods.
+     * @param hashCode hashcode of the item. This hashcode is processed from
+     *        the hashcode of the bootstrap method and the hashcode of
+     *        all bootstrap arguments.
+     */
+    void set(int position, int hashCode) {
+        this.type = ClassWriter.BSM;
+        this.intVal = position;
+        this.hashCode = hashCode;
+    }
+
+    /**
+     * Indicates if the given item is equal to this one. <i>This method assumes
+     * that the two items have the same {@link #type}</i>.
+     *
+     * @param i the item to be compared to this one. Both items must have the
+     *       same {@link #type}.
+     * @return <tt>true</tt> if the given item if equal to this one,
+     *         <tt>false</tt> otherwise.
+     */
+    boolean isEqualTo(final Item i) {
+        switch (type) {
+            case ClassWriter.UTF8:
+            case ClassWriter.STR:
+            case ClassWriter.CLASS:
+            case ClassWriter.MTYPE:
+            case ClassWriter.TYPE_NORMAL:
+                return i.strVal1.equals(strVal1);
+            case ClassWriter.TYPE_MERGED:
+            case ClassWriter.LONG:
+            case ClassWriter.DOUBLE:
+                return i.longVal == longVal;
+            case ClassWriter.INT:
+            case ClassWriter.FLOAT:
+                return i.intVal == intVal;
+            case ClassWriter.TYPE_UNINIT:
+                return i.intVal == intVal && i.strVal1.equals(strVal1);
+            case ClassWriter.NAME_TYPE:
+                return i.strVal1.equals(strVal1) && i.strVal2.equals(strVal2);
+            case ClassWriter.INDY:
+                return i.longVal == longVal && i.strVal1.equals(strVal1)
+                        && i.strVal2.equals(strVal2);
+
+            // case ClassWriter.FIELD:
+            // case ClassWriter.METH:
+            // case ClassWriter.IMETH:
+            // case ClassWriter.HANDLE_BASE + 1..9
+            default:
+                return i.strVal1.equals(strVal1) && i.strVal2.equals(strVal2)
+                        && i.strVal3.equals(strVal3);
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Label.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,584 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A label represents a position in the bytecode of a method. Labels are used
+ * for jump, goto, and switch instructions, and for try catch blocks. A label
+ * designates the <i>instruction</i> that is just after. Note however that
+ * there can be other elements between a label and the instruction it
+ * designates (such as other labels, stack map frames, line numbers, etc.).
+ *
+ * @author Eric Bruneton
+ */
+public class Label {
+
+    /**
+     * Indicates if this label is only used for debug attributes. Such a label
+     * is not the start of a basic block, the target of a jump instruction, or
+     * an exception handler. It can be safely ignored in control flow graph
+     * analysis algorithms (for optimization purposes).
+     */
+    static final int DEBUG = 1;
+
+    /**
+     * Indicates if the position of this label is known.
+     */
+    static final int RESOLVED = 2;
+
+    /**
+     * Indicates if this label has been updated, after instruction resizing.
+     */
+    static final int RESIZED = 4;
+
+    /**
+     * Indicates if this basic block has been pushed in the basic block stack.
+     * See {@link MethodWriter#visitMaxs visitMaxs}.
+     */
+    static final int PUSHED = 8;
+
+    /**
+     * Indicates if this label is the target of a jump instruction, or the start
+     * of an exception handler.
+     */
+    static final int TARGET = 16;
+
+    /**
+     * Indicates if a stack map frame must be stored for this label.
+     */
+    static final int STORE = 32;
+
+    /**
+     * Indicates if this label corresponds to a reachable basic block.
+     */
+    static final int REACHABLE = 64;
+
+    /**
+     * Indicates if this basic block ends with a JSR instruction.
+     */
+    static final int JSR = 128;
+
+    /**
+     * Indicates if this basic block ends with a RET instruction.
+     */
+    static final int RET = 256;
+
+    /**
+     * Indicates if this basic block is the start of a subroutine.
+     */
+    static final int SUBROUTINE = 512;
+
+    /**
+     * Indicates if this subroutine basic block has been visited by a
+     * visitSubroutine(null, ...) call.
+     */
+    static final int VISITED = 1024;
+
+    /**
+     * Indicates if this subroutine basic block has been visited by a
+     * visitSubroutine(!null, ...) call.
+     */
+    static final int VISITED2 = 2048;
+
+    /**
+     * Field used to associate user information to a label. Warning: this field
+     * is used by the ASM tree package. In order to use it with the ASM tree
+     * package you must override the {@link
+     * jdk.internal.org.objectweb.asm.tree.MethodNode#getLabelNode} method.
+     */
+    public Object info;
+
+    /**
+     * Flags that indicate the status of this label.
+     *
+     * @see #DEBUG
+     * @see #RESOLVED
+     * @see #RESIZED
+     * @see #PUSHED
+     * @see #TARGET
+     * @see #STORE
+     * @see #REACHABLE
+     * @see #JSR
+     * @see #RET
+     */
+    int status;
+
+    /**
+     * The line number corresponding to this label, if known.
+     */
+    int line;
+
+    /**
+     * The position of this label in the code, if known.
+     */
+    int position;
+
+    /**
+     * Number of forward references to this label, times two.
+     */
+    private int referenceCount;
+
+    /**
+     * Informations about forward references. Each forward reference is
+     * described by two consecutive integers in this array: the first one is the
+     * position of the first byte of the bytecode instruction that contains the
+     * forward reference, while the second is the position of the first byte of
+     * the forward reference itself. In fact the sign of the first integer
+     * indicates if this reference uses 2 or 4 bytes, and its absolute value
+     * gives the position of the bytecode instruction. This array is also used
+     * as a bitset to store the subroutines to which a basic block belongs. This
+     * information is needed in {@linked  MethodWriter#visitMaxs}, after all
+     * forward references have been resolved. Hence the same array can be used
+     * for both purposes without problems.
+     */
+    private int[] srcAndRefPositions;
+
+    // ------------------------------------------------------------------------
+
+    /*
+     * Fields for the control flow and data flow graph analysis algorithms (used
+     * to compute the maximum stack size or the stack map frames). A control
+     * flow graph contains one node per "basic block", and one edge per "jump"
+     * from one basic block to another. Each node (i.e., each basic block) is
+     * represented by the Label object that corresponds to the first instruction
+     * of this basic block. Each node also stores the list of its successors in
+     * the graph, as a linked list of Edge objects.
+     *
+     * The control flow analysis algorithms used to compute the maximum stack
+     * size or the stack map frames are similar and use two steps. The first
+     * step, during the visit of each instruction, builds information about the
+     * state of the local variables and the operand stack at the end of each
+     * basic block, called the "output frame", <i>relatively</i> to the frame
+     * state at the beginning of the basic block, which is called the "input
+     * frame", and which is <i>unknown</i> during this step. The second step,
+     * in {@link MethodWriter#visitMaxs}, is a fix point algorithm that
+     * computes information about the input frame of each basic block, from the
+     * input state of the first basic block (known from the method signature),
+     * and by the using the previously computed relative output frames.
+     *
+     * The algorithm used to compute the maximum stack size only computes the
+     * relative output and absolute input stack heights, while the algorithm
+     * used to compute stack map frames computes relative output frames and
+     * absolute input frames.
+     */
+
+    /**
+     * Start of the output stack relatively to the input stack. The exact
+     * semantics of this field depends on the algorithm that is used.
+     *
+     * When only the maximum stack size is computed, this field is the number of
+     * elements in the input stack.
+     *
+     * When the stack map frames are completely computed, this field is the
+     * offset of the first output stack element relatively to the top of the
+     * input stack. This offset is always negative or null. A null offset means
+     * that the output stack must be appended to the input stack. A -n offset
+     * means that the first n output stack elements must replace the top n input
+     * stack elements, and that the other elements must be appended to the input
+     * stack.
+     */
+    int inputStackTop;
+
+    /**
+     * Maximum height reached by the output stack, relatively to the top of the
+     * input stack. This maximum is always positive or null.
+     */
+    int outputStackMax;
+
+    /**
+     * Information about the input and output stack map frames of this basic
+     * block. This field is only used when {@link ClassWriter#COMPUTE_FRAMES}
+     * option is used.
+     */
+    Frame frame;
+
+    /**
+     * The successor of this label, in the order they are visited. This linked
+     * list does not include labels used for debug info only. If
+     * {@link ClassWriter#COMPUTE_FRAMES} option is used then, in addition, it
+     * does not contain successive labels that denote the same bytecode position
+     * (in this case only the first label appears in this list).
+     */
+    Label successor;
+
+    /**
+     * The successors of this node in the control flow graph. These successors
+     * are stored in a linked list of {@link Edge Edge} objects, linked to each
+     * other by their {@link Edge#next} field.
+     */
+    Edge successors;
+
+    /**
+     * The next basic block in the basic block stack. This stack is used in the
+     * main loop of the fix point algorithm used in the second step of the
+     * control flow analysis algorithms. It is also used in
+     * {@link #visitSubroutine} to avoid using a recursive method.
+     *
+     * @see MethodWriter#visitMaxs
+     */
+    Label next;
+
+    // ------------------------------------------------------------------------
+    // Constructor
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a new label.
+     */
+    public Label() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Methods to compute offsets and to manage forward references
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the offset corresponding to this label. This offset is computed
+     * from the start of the method's bytecode. <i>This method is intended for
+     * {@link Attribute} sub classes, and is normally not needed by class
+     * generators or adapters.</i>
+     *
+     * @return the offset corresponding to this label.
+     * @throws IllegalStateException if this label is not resolved yet.
+     */
+    public int getOffset() {
+        if ((status & RESOLVED) == 0) {
+            throw new IllegalStateException("Label offset position has not been resolved yet");
+        }
+        return position;
+    }
+
+    /**
+     * Puts a reference to this label in the bytecode of a method. If the
+     * position of the label is known, the offset is computed and written
+     * directly. Otherwise, a null offset is written and a new forward reference
+     * is declared for this label.
+     *
+     * @param owner the code writer that calls this method.
+     * @param out the bytecode of the method.
+     * @param source the position of first byte of the bytecode instruction that
+     *        contains this label.
+     * @param wideOffset <tt>true</tt> if the reference must be stored in 4
+     *        bytes, or <tt>false</tt> if it must be stored with 2 bytes.
+     * @throws IllegalArgumentException if this label has not been created by
+     *         the given code writer.
+     */
+    void put(
+        final MethodWriter owner,
+        final ByteVector out,
+        final int source,
+        final boolean wideOffset)
+    {
+        if ((status & RESOLVED) == 0) {
+            if (wideOffset) {
+                addReference(-1 - source, out.length);
+                out.putInt(-1);
+            } else {
+                addReference(source, out.length);
+                out.putShort(-1);
+            }
+        } else {
+            if (wideOffset) {
+                out.putInt(position - source);
+            } else {
+                out.putShort(position - source);
+            }
+        }
+    }
+
+    /**
+     * Adds a forward reference to this label. This method must be called only
+     * for a true forward reference, i.e. only if this label is not resolved
+     * yet. For backward references, the offset of the reference can be, and
+     * must be, computed and stored directly.
+     *
+     * @param sourcePosition the position of the referencing instruction. This
+     *        position will be used to compute the offset of this forward
+     *        reference.
+     * @param referencePosition the position where the offset for this forward
+     *        reference must be stored.
+     */
+    private void addReference(
+        final int sourcePosition,
+        final int referencePosition)
+    {
+        if (srcAndRefPositions == null) {
+            srcAndRefPositions = new int[6];
+        }
+        if (referenceCount >= srcAndRefPositions.length) {
+            int[] a = new int[srcAndRefPositions.length + 6];
+            System.arraycopy(srcAndRefPositions,
+                    0,
+                    a,
+                    0,
+                    srcAndRefPositions.length);
+            srcAndRefPositions = a;
+        }
+        srcAndRefPositions[referenceCount++] = sourcePosition;
+        srcAndRefPositions[referenceCount++] = referencePosition;
+    }
+
+    /**
+     * Resolves all forward references to this label. This method must be called
+     * when this label is added to the bytecode of the method, i.e. when its
+     * position becomes known. This method fills in the blanks that where left
+     * in the bytecode by each forward reference previously added to this label.
+     *
+     * @param owner the code writer that calls this method.
+     * @param position the position of this label in the bytecode.
+     * @param data the bytecode of the method.
+     * @return <tt>true</tt> if a blank that was left for this label was to
+     *         small to store the offset. In such a case the corresponding jump
+     *         instruction is replaced with a pseudo instruction (using unused
+     *         opcodes) using an unsigned two bytes offset. These pseudo
+     *         instructions will need to be replaced with true instructions with
+     *         wider offsets (4 bytes instead of 2). This is done in
+     *         {@link MethodWriter#resizeInstructions}.
+     * @throws IllegalArgumentException if this label has already been resolved,
+     *         or if it has not been created by the given code writer.
+     */
+    boolean resolve(
+        final MethodWriter owner,
+        final int position,
+        final byte[] data)
+    {
+        boolean needUpdate = false;
+        this.status |= RESOLVED;
+        this.position = position;
+        int i = 0;
+        while (i < referenceCount) {
+            int source = srcAndRefPositions[i++];
+            int reference = srcAndRefPositions[i++];
+            int offset;
+            if (source >= 0) {
+                offset = position - source;
+                if (offset < Short.MIN_VALUE || offset > Short.MAX_VALUE) {
+                    /*
+                     * changes the opcode of the jump instruction, in order to
+                     * be able to find it later (see resizeInstructions in
+                     * MethodWriter). These temporary opcodes are similar to
+                     * jump instruction opcodes, except that the 2 bytes offset
+                     * is unsigned (and can therefore represent values from 0 to
+                     * 65535, which is sufficient since the size of a method is
+                     * limited to 65535 bytes).
+                     */
+                    int opcode = data[reference - 1] & 0xFF;
+                    if (opcode <= Opcodes.JSR) {
+                        // changes IFEQ ... JSR to opcodes 202 to 217
+                        data[reference - 1] = (byte) (opcode + 49);
+                    } else {
+                        // changes IFNULL and IFNONNULL to opcodes 218 and 219
+                        data[reference - 1] = (byte) (opcode + 20);
+                    }
+                    needUpdate = true;
+                }
+                data[reference++] = (byte) (offset >>> 8);
+                data[reference] = (byte) offset;
+            } else {
+                offset = position + source + 1;
+                data[reference++] = (byte) (offset >>> 24);
+                data[reference++] = (byte) (offset >>> 16);
+                data[reference++] = (byte) (offset >>> 8);
+                data[reference] = (byte) offset;
+            }
+        }
+        return needUpdate;
+    }
+
+    /**
+     * Returns the first label of the series to which this label belongs. For an
+     * isolated label or for the first label in a series of successive labels,
+     * this method returns the label itself. For other labels it returns the
+     * first label of the series.
+     *
+     * @return the first label of the series to which this label belongs.
+     */
+    Label getFirst() {
+        return !ClassReader.FRAMES || frame == null ? this : frame.owner;
+    }
+
+    // ------------------------------------------------------------------------
+    // Methods related to subroutines
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns true is this basic block belongs to the given subroutine.
+     *
+     * @param id a subroutine id.
+     * @return true is this basic block belongs to the given subroutine.
+     */
+    boolean inSubroutine(final long id) {
+        if ((status & Label.VISITED) != 0) {
+            return (srcAndRefPositions[(int) (id >>> 32)] & (int) id) != 0;
+        }
+        return false;
+    }
+
+    /**
+     * Returns true if this basic block and the given one belong to a common
+     * subroutine.
+     *
+     * @param block another basic block.
+     * @return true if this basic block and the given one belong to a common
+     *         subroutine.
+     */
+    boolean inSameSubroutine(final Label block) {
+        if ((status & VISITED) == 0 || (block.status & VISITED) == 0) {
+            return false;
+        }
+        for (int i = 0; i < srcAndRefPositions.length; ++i) {
+            if ((srcAndRefPositions[i] & block.srcAndRefPositions[i]) != 0) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    /**
+     * Marks this basic block as belonging to the given subroutine.
+     *
+     * @param id a subroutine id.
+     * @param nbSubroutines the total number of subroutines in the method.
+     */
+    void addToSubroutine(final long id, final int nbSubroutines) {
+        if ((status & VISITED) == 0) {
+            status |= VISITED;
+            srcAndRefPositions = new int[(nbSubroutines - 1) / 32 + 1];
+        }
+        srcAndRefPositions[(int) (id >>> 32)] |= (int) id;
+    }
+
+    /**
+     * Finds the basic blocks that belong to a given subroutine, and marks these
+     * blocks as belonging to this subroutine. This method follows the control
+     * flow graph to find all the blocks that are reachable from the current
+     * block WITHOUT following any JSR target.
+     *
+     * @param JSR a JSR block that jumps to this subroutine. If this JSR is not
+     *        null it is added to the successor of the RET blocks found in the
+     *        subroutine.
+     * @param id the id of this subroutine.
+     * @param nbSubroutines the total number of subroutines in the method.
+     */
+    void visitSubroutine(final Label JSR, final long id, final int nbSubroutines)
+    {
+        // user managed stack of labels, to avoid using a recursive method
+        // (recursivity can lead to stack overflow with very large methods)
+        Label stack = this;
+        while (stack != null) {
+            // removes a label l from the stack
+            Label l = stack;
+            stack = l.next;
+            l.next = null;
+
+            if (JSR != null) {
+                if ((l.status & VISITED2) != 0) {
+                    continue;
+                }
+                l.status |= VISITED2;
+                // adds JSR to the successors of l, if it is a RET block
+                if ((l.status & RET) != 0) {
+                    if (!l.inSameSubroutine(JSR)) {
+                        Edge e = new Edge();
+                        e.info = l.inputStackTop;
+                        e.successor = JSR.successors.successor;
+                        e.next = l.successors;
+                        l.successors = e;
+                    }
+                }
+            } else {
+                // if the l block already belongs to subroutine 'id', continue
+                if (l.inSubroutine(id)) {
+                    continue;
+                }
+                // marks the l block as belonging to subroutine 'id'
+                l.addToSubroutine(id, nbSubroutines);
+            }
+            // pushes each successor of l on the stack, except JSR targets
+            Edge e = l.successors;
+            while (e != null) {
+                // if the l block is a JSR block, then 'l.successors.next' leads
+                // to the JSR target (see {@link #visitJumpInsn}) and must
+                // therefore not be followed
+                if ((l.status & Label.JSR) == 0 || e != l.successors.next) {
+                    // pushes e.successor on the stack if it not already added
+                    if (e.successor.next == null) {
+                        e.successor.next = stack;
+                        stack = e.successor;
+                    }
+                }
+                e = e.next;
+            }
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Overriden Object methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns a string representation of this label.
+     *
+     * @return a string representation of this label.
+     */
+    @Override
+    public String toString() {
+        return "L" + System.identityHashCode(this);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/MethodVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,617 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A visitor to visit a Java method. The methods of this class must be
+ * called in the following order: [ <tt>visitAnnotationDefault</tt> ] (
+ * <tt>visitAnnotation</tt> | <tt>visitParameterAnnotation</tt> |
+ * <tt>visitAttribute</tt> )* [ <tt>visitCode</tt> ( <tt>visitFrame</tt> |
+ * <tt>visit</tt><i>X</i>Insn</tt> | <tt>visitLabel</tt> | <tt>visitTryCatchBlock</tt> |
+ * <tt>visitLocalVariable</tt> | <tt>visitLineNumber</tt> )* <tt>visitMaxs</tt> ]
+ * <tt>visitEnd</tt>. In addition, the <tt>visit</tt><i>X</i>Insn</tt>
+ * and <tt>visitLabel</tt> methods must be called in the sequential order of
+ * the bytecode instructions of the visited code, <tt>visitTryCatchBlock</tt>
+ * must be called <i>before</i> the labels passed as arguments have been
+ * visited, and the <tt>visitLocalVariable</tt> and <tt>visitLineNumber</tt>
+ * methods must be called <i>after</i> the labels passed as arguments have been
+ * visited.
+ *
+ * @author Eric Bruneton
+ */
+public abstract class MethodVisitor {
+
+    /**
+     * The ASM API version implemented by this visitor. The value of this field
+     * must be one of {@link Opcodes#ASM4}.
+     */
+    protected final int api;
+
+    /**
+     * The method visitor to which this visitor must delegate method calls. May
+     * be null.
+     */
+    protected MethodVisitor mv;
+
+    /**
+     * Constructs a new {@link MethodVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public MethodVisitor(final int api) {
+        this(api, null);
+    }
+
+    /**
+     * Constructs a new {@link MethodVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param mv the method visitor to which this visitor must delegate method
+     *        calls. May be null.
+     */
+    public MethodVisitor(final int api, final MethodVisitor mv) {
+        /*if (api != Opcodes.ASM4) {
+            throw new IllegalArgumentException();
+        }*/
+        this.api = api;
+        this.mv = mv;
+    }
+
+    // -------------------------------------------------------------------------
+    // Annotations and non standard attributes
+    // -------------------------------------------------------------------------
+
+    /**
+     * Visits the default value of this annotation interface method.
+     *
+     * @return a visitor to the visit the actual default value of this
+     *         annotation interface method, or <tt>null</tt> if this visitor
+     *         is not interested in visiting this default value. The 'name'
+     *         parameters passed to the methods of this annotation visitor are
+     *         ignored. Moreover, exacly one visit method must be called on this
+     *         annotation visitor, followed by visitEnd.
+     */
+    public AnnotationVisitor visitAnnotationDefault() {
+        if (mv != null) {
+            return mv.visitAnnotationDefault();
+        }
+        return null;
+    }
+
+    /**
+     * Visits an annotation of this method.
+     *
+     * @param desc the class descriptor of the annotation class.
+     * @param visible <tt>true</tt> if the annotation is visible at runtime.
+     * @return a visitor to visit the annotation values, or <tt>null</tt> if
+     *         this visitor is not interested in visiting this annotation.
+     */
+    public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
+        if (mv != null) {
+            return mv.visitAnnotation(desc, visible);
+        }
+        return null;
+    }
+
+    /**
+     * Visits an annotation of a parameter this method.
+     *
+     * @param parameter the parameter index.
+     * @param desc the class descriptor of the annotation class.
+     * @param visible <tt>true</tt> if the annotation is visible at runtime.
+     * @return a visitor to visit the annotation values, or <tt>null</tt> if
+     *         this visitor is not interested in visiting this annotation.
+     */
+    public AnnotationVisitor visitParameterAnnotation(
+        int parameter,
+        String desc,
+        boolean visible)
+    {
+        if (mv != null) {
+            return mv.visitParameterAnnotation(parameter, desc, visible);
+        }
+        return null;
+    }
+
+    /**
+     * Visits a non standard attribute of this method.
+     *
+     * @param attr an attribute.
+     */
+    public void visitAttribute(Attribute attr) {
+        if (mv != null) {
+            mv.visitAttribute(attr);
+        }
+    }
+
+    /**
+     * Starts the visit of the method's code, if any (i.e. non abstract method).
+     */
+    public void visitCode() {
+        if (mv != null) {
+            mv.visitCode();
+        }
+    }
+
+    /**
+     * Visits the current state of the local variables and operand stack
+     * elements. This method must(*) be called <i>just before</i> any
+     * instruction <b>i</b> that follows an unconditional branch instruction
+     * such as GOTO or THROW, that is the target of a jump instruction, or that
+     * starts an exception handler block. The visited types must describe the
+     * values of the local variables and of the operand stack elements <i>just
+     * before</i> <b>i</b> is executed. <br> <br> (*) this is mandatory only
+     * for classes whose version is greater than or equal to
+     * {@link Opcodes#V1_6 V1_6}. <br> <br> Packed frames are basically
+     * "deltas" from the state of the previous frame (very first frame is
+     * implicitly defined by the method's parameters and access flags): <ul>
+     * <li>{@link Opcodes#F_SAME} representing frame with exactly the same
+     * locals as the previous frame and with the empty stack.</li> <li>{@link Opcodes#F_SAME1}
+     * representing frame with exactly the same locals as the previous frame and
+     * with single value on the stack (<code>nStack</code> is 1 and
+     * <code>stack[0]</code> contains value for the type of the stack item).</li>
+     * <li>{@link Opcodes#F_APPEND} representing frame with current locals are
+     * the same as the locals in the previous frame, except that additional
+     * locals are defined (<code>nLocal</code> is 1, 2 or 3 and
+     * <code>local</code> elements contains values representing added types).</li>
+     * <li>{@link Opcodes#F_CHOP} representing frame with current locals are
+     * the same as the locals in the previous frame, except that the last 1-3
+     * locals are absent and with the empty stack (<code>nLocals</code> is 1,
+     * 2 or 3). </li> <li>{@link Opcodes#F_FULL} representing complete frame
+     * data.</li> </li> </ul>
+     *
+     * @param type the type of this stack map frame. Must be
+     *        {@link Opcodes#F_NEW} for expanded frames, or
+     *        {@link Opcodes#F_FULL}, {@link Opcodes#F_APPEND},
+     *        {@link Opcodes#F_CHOP}, {@link Opcodes#F_SAME} or
+     *        {@link Opcodes#F_APPEND}, {@link Opcodes#F_SAME1} for compressed
+     *        frames.
+     * @param nLocal the number of local variables in the visited frame.
+     * @param local the local variable types in this frame. This array must not
+     *        be modified. Primitive types are represented by
+     *        {@link Opcodes#TOP}, {@link Opcodes#INTEGER},
+     *        {@link Opcodes#FLOAT}, {@link Opcodes#LONG},
+     *        {@link Opcodes#DOUBLE},{@link Opcodes#NULL} or
+     *        {@link Opcodes#UNINITIALIZED_THIS} (long and double are
+     *        represented by a single element). Reference types are represented
+     *        by String objects (representing internal names), and uninitialized
+     *        types by Label objects (this label designates the NEW instruction
+     *        that created this uninitialized value).
+     * @param nStack the number of operand stack elements in the visited frame.
+     * @param stack the operand stack types in this frame. This array must not
+     *        be modified. Its content has the same format as the "local" array.
+     * @throws IllegalStateException if a frame is visited just after another
+     *        one, without any instruction between the two (unless this frame
+     *        is a Opcodes#F_SAME frame, in which case it is silently ignored).
+     */
+    public void visitFrame(
+        int type,
+        int nLocal,
+        Object[] local,
+        int nStack,
+        Object[] stack)
+    {
+        if (mv != null) {
+            mv.visitFrame(type, nLocal, local, nStack, stack);
+        }
+    }
+
+    // -------------------------------------------------------------------------
+    // Normal instructions
+    // -------------------------------------------------------------------------
+
+    /**
+     * Visits a zero operand instruction.
+     *
+     * @param opcode the opcode of the instruction to be visited. This opcode is
+     *        either NOP, ACONST_NULL, ICONST_M1, ICONST_0, ICONST_1, ICONST_2,
+     *        ICONST_3, ICONST_4, ICONST_5, LCONST_0, LCONST_1, FCONST_0,
+     *        FCONST_1, FCONST_2, DCONST_0, DCONST_1, IALOAD, LALOAD, FALOAD,
+     *        DALOAD, AALOAD, BALOAD, CALOAD, SALOAD, IASTORE, LASTORE, FASTORE,
+     *        DASTORE, AASTORE, BASTORE, CASTORE, SASTORE, POP, POP2, DUP,
+     *        DUP_X1, DUP_X2, DUP2, DUP2_X1, DUP2_X2, SWAP, IADD, LADD, FADD,
+     *        DADD, ISUB, LSUB, FSUB, DSUB, IMUL, LMUL, FMUL, DMUL, IDIV, LDIV,
+     *        FDIV, DDIV, IREM, LREM, FREM, DREM, INEG, LNEG, FNEG, DNEG, ISHL,
+     *        LSHL, ISHR, LSHR, IUSHR, LUSHR, IAND, LAND, IOR, LOR, IXOR, LXOR,
+     *        I2L, I2F, I2D, L2I, L2F, L2D, F2I, F2L, F2D, D2I, D2L, D2F, I2B,
+     *        I2C, I2S, LCMP, FCMPL, FCMPG, DCMPL, DCMPG, IRETURN, LRETURN,
+     *        FRETURN, DRETURN, ARETURN, RETURN, ARRAYLENGTH, ATHROW,
+     *        MONITORENTER, or MONITOREXIT.
+     */
+    public void visitInsn(int opcode) {
+        if (mv != null) {
+            mv.visitInsn(opcode);
+        }
+    }
+
+    /**
+     * Visits an instruction with a single int operand.
+     *
+     * @param opcode the opcode of the instruction to be visited. This opcode is
+     *        either BIPUSH, SIPUSH or NEWARRAY.
+     * @param operand the operand of the instruction to be visited.<br> When
+     *        opcode is BIPUSH, operand value should be between Byte.MIN_VALUE
+     *        and Byte.MAX_VALUE.<br> When opcode is SIPUSH, operand value
+     *        should be between Short.MIN_VALUE and Short.MAX_VALUE.<br> When
+     *        opcode is NEWARRAY, operand value should be one of
+     *        {@link Opcodes#T_BOOLEAN}, {@link Opcodes#T_CHAR},
+     *        {@link Opcodes#T_FLOAT}, {@link Opcodes#T_DOUBLE},
+     *        {@link Opcodes#T_BYTE}, {@link Opcodes#T_SHORT},
+     *        {@link Opcodes#T_INT} or {@link Opcodes#T_LONG}.
+     */
+    public void visitIntInsn(int opcode, int operand) {
+        if (mv != null) {
+            mv.visitIntInsn(opcode, operand);
+        }
+    }
+
+    /**
+     * Visits a local variable instruction. A local variable instruction is an
+     * instruction that loads or stores the value of a local variable.
+     *
+     * @param opcode the opcode of the local variable instruction to be visited.
+     *        This opcode is either ILOAD, LLOAD, FLOAD, DLOAD, ALOAD, ISTORE,
+     *        LSTORE, FSTORE, DSTORE, ASTORE or RET.
+     * @param var the operand of the instruction to be visited. This operand is
+     *        the index of a local variable.
+     */
+    public void visitVarInsn(int opcode, int var) {
+        if (mv != null) {
+            mv.visitVarInsn(opcode, var);
+        }
+    }
+
+    /**
+     * Visits a type instruction. A type instruction is an instruction that
+     * takes the internal name of a class as parameter.
+     *
+     * @param opcode the opcode of the type instruction to be visited. This
+     *        opcode is either NEW, ANEWARRAY, CHECKCAST or INSTANCEOF.
+     * @param type the operand of the instruction to be visited. This operand
+     *        must be the internal name of an object or array class (see {@link
+     *        Type#getInternalName() getInternalName}).
+     */
+    public void visitTypeInsn(int opcode, String type) {
+        if (mv != null) {
+            mv.visitTypeInsn(opcode, type);
+        }
+    }
+
+    /**
+     * Visits a field instruction. A field instruction is an instruction that
+     * loads or stores the value of a field of an object.
+     *
+     * @param opcode the opcode of the type instruction to be visited. This
+     *        opcode is either GETSTATIC, PUTSTATIC, GETFIELD or PUTFIELD.
+     * @param owner the internal name of the field's owner class (see {@link
+     *        Type#getInternalName() getInternalName}).
+     * @param name the field's name.
+     * @param desc the field's descriptor (see {@link Type Type}).
+     */
+    public void visitFieldInsn(int opcode, String owner, String name, String desc) {
+        if (mv != null) {
+            mv.visitFieldInsn(opcode, owner, name, desc);
+        }
+    }
+
+    /**
+     * Visits a method instruction. A method instruction is an instruction that
+     * invokes a method.
+     *
+     * @param opcode the opcode of the type instruction to be visited. This
+     *        opcode is either INVOKEVIRTUAL, INVOKESPECIAL, INVOKESTATIC
+     *        or INVOKEINTERFACE.
+     * @param owner the internal name of the method's owner class (see {@link
+     *        Type#getInternalName() getInternalName}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     */
+    public void visitMethodInsn(int opcode, String owner, String name, String desc) {
+        if (mv != null) {
+            mv.visitMethodInsn(opcode, owner, name, desc);
+        }
+    }
+
+    /**
+     * Visits an invokedynamic instruction.
+     *
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param bsm the bootstrap method.
+     * @param bsmArgs the bootstrap method constant arguments. Each argument
+     *        must be an {@link Integer}, {@link Float}, {@link Long},
+     *        {@link Double}, {@link String}, {@link Type} or {@link Handle}
+     *        value. This method is allowed to modify the content of the array
+     *        so a caller should expect that this array may change.
+     */
+    public void visitInvokeDynamicInsn(String name, String desc, Handle bsm, Object... bsmArgs) {
+        if (mv != null) {
+            mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+        }
+    }
+
+    /**
+     * Visits a jump instruction. A jump instruction is an instruction that may
+     * jump to another instruction.
+     *
+     * @param opcode the opcode of the type instruction to be visited. This
+     *        opcode is either IFEQ, IFNE, IFLT, IFGE, IFGT, IFLE, IF_ICMPEQ,
+     *        IF_ICMPNE, IF_ICMPLT, IF_ICMPGE, IF_ICMPGT, IF_ICMPLE, IF_ACMPEQ,
+     *        IF_ACMPNE, GOTO, JSR, IFNULL or IFNONNULL.
+     * @param label the operand of the instruction to be visited. This operand
+     *        is a label that designates the instruction to which the jump
+     *        instruction may jump.
+     */
+    public void visitJumpInsn(int opcode, Label label) {
+        if (mv != null) {
+            mv.visitJumpInsn(opcode, label);
+        }
+    }
+
+    /**
+     * Visits a label. A label designates the instruction that will be visited
+     * just after it.
+     *
+     * @param label a {@link Label Label} object.
+     */
+    public void visitLabel(Label label) {
+        if (mv != null) {
+            mv.visitLabel(label);
+        }
+    }
+
+    // -------------------------------------------------------------------------
+    // Special instructions
+    // -------------------------------------------------------------------------
+
+    /**
+     * Visits a LDC instruction. Note that new constant types may be added in
+     * future versions of the Java Virtual Machine. To easily detect new
+     * constant types, implementations of this method should check for
+     * unexpected constant types, like this:
+     * <pre>
+     * if (cst instanceof Integer) {
+     *   // ...
+     * } else if (cst instanceof Float) {
+     *   // ...
+     * } else if (cst instanceof Long) {
+     *   // ...
+     * } else if (cst instanceof Double) {
+     *   // ...
+     * } else if (cst instanceof String) {
+     *   // ...
+     * } else if (cst instanceof Type) {
+     *   int sort = ((Type) cst).getSort();
+     *   if (sort == Type.OBJECT) {
+     *     // ...
+     *   } else if (sort == Type.ARRAY) {
+     *     // ...
+     *   } else if (sort == Type.METHOD) {
+     *     // ...
+     *   } else {
+     *     // throw an exception
+     *   }
+     * } else if (cst instanceof Handle) {
+     *   // ...
+     * } else {
+     *   // throw an exception
+     * }</pre>
+     *
+     * @param cst the constant to be loaded on the stack. This parameter must be
+     *        a non null {@link Integer}, a {@link Float}, a {@link Long}, a
+     *        {@link Double}, a {@link String}, a {@link Type} of OBJECT or ARRAY
+     *        sort for <tt>.class</tt> constants, for classes whose version is
+     *        49.0, a {@link Type} of METHOD sort or a {@link Handle} for
+     *        MethodType and MethodHandle constants, for classes whose version
+     *        is 51.0.
+     */
+    public void visitLdcInsn(Object cst) {
+        if (mv != null) {
+            mv.visitLdcInsn(cst);
+        }
+    }
+
+    /**
+     * Visits an IINC instruction.
+     *
+     * @param var index of the local variable to be incremented.
+     * @param increment amount to increment the local variable by.
+     */
+    public void visitIincInsn(int var, int increment) {
+        if (mv != null) {
+            mv.visitIincInsn(var, increment);
+        }
+    }
+
+    /**
+     * Visits a TABLESWITCH instruction.
+     *
+     * @param min the minimum key value.
+     * @param max the maximum key value.
+     * @param dflt beginning of the default handler block.
+     * @param labels beginnings of the handler blocks. <tt>labels[i]</tt> is
+     *        the beginning of the handler block for the <tt>min + i</tt> key.
+     */
+    public void visitTableSwitchInsn(int min, int max, Label dflt, Label... labels) {
+        if (mv != null) {
+            mv.visitTableSwitchInsn(min, max, dflt, labels);
+        }
+    }
+
+    /**
+     * Visits a LOOKUPSWITCH instruction.
+     *
+     * @param dflt beginning of the default handler block.
+     * @param keys the values of the keys.
+     * @param labels beginnings of the handler blocks. <tt>labels[i]</tt> is
+     *        the beginning of the handler block for the <tt>keys[i]</tt> key.
+     */
+    public void visitLookupSwitchInsn(Label dflt, int[] keys, Label[] labels) {
+        if (mv != null) {
+            mv.visitLookupSwitchInsn(dflt, keys, labels);
+        }
+    }
+
+    /**
+     * Visits a MULTIANEWARRAY instruction.
+     *
+     * @param desc an array type descriptor (see {@link Type Type}).
+     * @param dims number of dimensions of the array to allocate.
+     */
+    public void visitMultiANewArrayInsn(String desc, int dims) {
+        if (mv != null) {
+            mv.visitMultiANewArrayInsn(desc, dims);
+        }
+    }
+
+    // -------------------------------------------------------------------------
+    // Exceptions table entries, debug information, max stack and max locals
+    // -------------------------------------------------------------------------
+
+    /**
+     * Visits a try catch block.
+     *
+     * @param start beginning of the exception handler's scope (inclusive).
+     * @param end end of the exception handler's scope (exclusive).
+     * @param handler beginning of the exception handler's code.
+     * @param type internal name of the type of exceptions handled by the
+     *        handler, or <tt>null</tt> to catch any exceptions (for "finally"
+     *        blocks).
+     * @throws IllegalArgumentException if one of the labels has already been
+     *         visited by this visitor (by the {@link #visitLabel visitLabel}
+     *         method).
+     */
+    public void visitTryCatchBlock(Label start, Label end, Label handler, String type) {
+        if (mv != null) {
+            mv.visitTryCatchBlock(start, end, handler, type);
+        }
+    }
+
+    /**
+     * Visits a local variable declaration.
+     *
+     * @param name the name of a local variable.
+     * @param desc the type descriptor of this local variable.
+     * @param signature the type signature of this local variable. May be
+     *        <tt>null</tt> if the local variable type does not use generic
+     *        types.
+     * @param start the first instruction corresponding to the scope of this
+     *        local variable (inclusive).
+     * @param end the last instruction corresponding to the scope of this local
+     *        variable (exclusive).
+     * @param index the local variable's index.
+     * @throws IllegalArgumentException if one of the labels has not already
+     *         been visited by this visitor (by the
+     *         {@link #visitLabel visitLabel} method).
+     */
+    public void visitLocalVariable(
+        String name,
+        String desc,
+        String signature,
+        Label start,
+        Label end,
+        int index)
+    {
+        if (mv != null) {
+            mv.visitLocalVariable(name, desc, signature, start, end, index);
+        }
+    }
+
+    /**
+     * Visits a line number declaration.
+     *
+     * @param line a line number. This number refers to the source file from
+     *        which the class was compiled.
+     * @param start the first instruction corresponding to this line number.
+     * @throws IllegalArgumentException if <tt>start</tt> has not already been
+     *         visited by this visitor (by the {@link #visitLabel visitLabel}
+     *         method).
+     */
+    public void visitLineNumber(int line, Label start) {
+        if (mv != null) {
+            mv.visitLineNumber(line, start);
+        }
+    }
+
+    /**
+     * Visits the maximum stack size and the maximum number of local variables
+     * of the method.
+     *
+     * @param maxStack maximum stack size of the method.
+     * @param maxLocals maximum number of local variables for the method.
+     */
+    public void visitMaxs(int maxStack, int maxLocals) {
+        if (mv != null) {
+            mv.visitMaxs(maxStack, maxLocals);
+        }
+    }
+
+    /**
+     * Visits the end of the method. This method, which is the last one to be
+     * called, is used to inform the visitor that all the annotations and
+     * attributes of the method have been visited.
+     */
+    public void visitEnd() {
+        if (mv != null) {
+            mv.visitEnd();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/MethodWriter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,2695 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * A {@link MethodVisitor} that generates methods in bytecode form. Each visit
+ * method of this class appends the bytecode corresponding to the visited
+ * instruction to a byte vector, in the order these methods are called.
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+class MethodWriter extends MethodVisitor {
+
+    /**
+     * Pseudo access flag used to denote constructors.
+     */
+    static final int ACC_CONSTRUCTOR = 262144;
+
+    /**
+     * Frame has exactly the same locals as the previous stack map frame and
+     * number of stack items is zero.
+     */
+    static final int SAME_FRAME = 0; // to 63 (0-3f)
+
+    /**
+     * Frame has exactly the same locals as the previous stack map frame and
+     * number of stack items is 1
+     */
+    static final int SAME_LOCALS_1_STACK_ITEM_FRAME = 64; // to 127 (40-7f)
+
+    /**
+     * Reserved for future use
+     */
+    static final int RESERVED = 128;
+
+    /**
+     * Frame has exactly the same locals as the previous stack map frame and
+     * number of stack items is 1. Offset is bigger then 63;
+     */
+    static final int SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED = 247; // f7
+
+    /**
+     * Frame where current locals are the same as the locals in the previous
+     * frame, except that the k last locals are absent. The value of k is given
+     * by the formula 251-frame_type.
+     */
+    static final int CHOP_FRAME = 248; // to 250 (f8-fA)
+
+    /**
+     * Frame has exactly the same locals as the previous stack map frame and
+     * number of stack items is zero. Offset is bigger then 63;
+     */
+    static final int SAME_FRAME_EXTENDED = 251; // fb
+
+    /**
+     * Frame where current locals are the same as the locals in the previous
+     * frame, except that k additional locals are defined. The value of k is
+     * given by the formula frame_type-251.
+     */
+    static final int APPEND_FRAME = 252; // to 254 // fc-fe
+
+    /**
+     * Full frame
+     */
+    static final int FULL_FRAME = 255; // ff
+
+    /**
+     * Indicates that the stack map frames must be recomputed from scratch. In
+     * this case the maximum stack size and number of local variables is also
+     * recomputed from scratch.
+     *
+     * @see #compute
+     */
+    private static final int FRAMES = 0;
+
+    /**
+     * Indicates that the maximum stack size and number of local variables must
+     * be automatically computed.
+     *
+     * @see #compute
+     */
+    private static final int MAXS = 1;
+
+    /**
+     * Indicates that nothing must be automatically computed.
+     *
+     * @see #compute
+     */
+    private static final int NOTHING = 2;
+
+    /**
+     * The class writer to which this method must be added.
+     */
+    final ClassWriter cw;
+
+    /**
+     * Access flags of this method.
+     */
+    private int access;
+
+    /**
+     * The index of the constant pool item that contains the name of this
+     * method.
+     */
+    private final int name;
+
+    /**
+     * The index of the constant pool item that contains the descriptor of this
+     * method.
+     */
+    private final int desc;
+
+    /**
+     * The descriptor of this method.
+     */
+    private final String descriptor;
+
+    /**
+     * The signature of this method.
+     */
+    String signature;
+
+    /**
+     * If not zero, indicates that the code of this method must be copied from
+     * the ClassReader associated to this writer in <code>cw.cr</code>. More
+     * precisely, this field gives the index of the first byte to copied from
+     * <code>cw.cr.b</code>.
+     */
+    int classReaderOffset;
+
+    /**
+     * If not zero, indicates that the code of this method must be copied from
+     * the ClassReader associated to this writer in <code>cw.cr</code>. More
+     * precisely, this field gives the number of bytes to copied from
+     * <code>cw.cr.b</code>.
+     */
+    int classReaderLength;
+
+    /**
+     * Number of exceptions that can be thrown by this method.
+     */
+    int exceptionCount;
+
+    /**
+     * The exceptions that can be thrown by this method. More precisely, this
+     * array contains the indexes of the constant pool items that contain the
+     * internal names of these exception classes.
+     */
+    int[] exceptions;
+
+    /**
+     * The annotation default attribute of this method. May be <tt>null</tt>.
+     */
+    private ByteVector annd;
+
+    /**
+     * The runtime visible annotations of this method. May be <tt>null</tt>.
+     */
+    private AnnotationWriter anns;
+
+    /**
+     * The runtime invisible annotations of this method. May be <tt>null</tt>.
+     */
+    private AnnotationWriter ianns;
+
+    /**
+     * The runtime visible parameter annotations of this method. May be
+     * <tt>null</tt>.
+     */
+    private AnnotationWriter[] panns;
+
+    /**
+     * The runtime invisible parameter annotations of this method. May be
+     * <tt>null</tt>.
+     */
+    private AnnotationWriter[] ipanns;
+
+    /**
+     * The number of synthetic parameters of this method.
+     */
+    private int synthetics;
+
+    /**
+     * The non standard attributes of the method.
+     */
+    private Attribute attrs;
+
+    /**
+     * The bytecode of this method.
+     */
+    private ByteVector code = new ByteVector();
+
+    /**
+     * Maximum stack size of this method.
+     */
+    private int maxStack;
+
+    /**
+     * Maximum number of local variables for this method.
+     */
+    private int maxLocals;
+
+    /**
+     *  Number of local variables in the current stack map frame.
+     */
+    private int currentLocals;
+
+    /**
+     * Number of stack map frames in the StackMapTable attribute.
+     */
+    private int frameCount;
+
+    /**
+     * The StackMapTable attribute.
+     */
+    private ByteVector stackMap;
+
+    /**
+     * The offset of the last frame that was written in the StackMapTable
+     * attribute.
+     */
+    private int previousFrameOffset;
+
+    /**
+     * The last frame that was written in the StackMapTable attribute.
+     *
+     * @see #frame
+     */
+    private int[] previousFrame;
+
+    /**
+     * Index of the next element to be added in {@link #frame}.
+     */
+    private int frameIndex;
+
+    /**
+     * The current stack map frame. The first element contains the offset of the
+     * instruction to which the frame corresponds, the second element is the
+     * number of locals and the third one is the number of stack elements. The
+     * local variables start at index 3 and are followed by the operand stack
+     * values. In summary frame[0] = offset, frame[1] = nLocal, frame[2] =
+     * nStack, frame[3] = nLocal. All types are encoded as integers, with the
+     * same format as the one used in {@link Label}, but limited to BASE types.
+     */
+    private int[] frame;
+
+    /**
+     * Number of elements in the exception handler list.
+     */
+    private int handlerCount;
+
+    /**
+     * The first element in the exception handler list.
+     */
+    private Handler firstHandler;
+
+    /**
+     * The last element in the exception handler list.
+     */
+    private Handler lastHandler;
+
+    /**
+     * Number of entries in the LocalVariableTable attribute.
+     */
+    private int localVarCount;
+
+    /**
+     * The LocalVariableTable attribute.
+     */
+    private ByteVector localVar;
+
+    /**
+     * Number of entries in the LocalVariableTypeTable attribute.
+     */
+    private int localVarTypeCount;
+
+    /**
+     * The LocalVariableTypeTable attribute.
+     */
+    private ByteVector localVarType;
+
+    /**
+     * Number of entries in the LineNumberTable attribute.
+     */
+    private int lineNumberCount;
+
+    /**
+     * The LineNumberTable attribute.
+     */
+    private ByteVector lineNumber;
+
+    /**
+     * The non standard attributes of the method's code.
+     */
+    private Attribute cattrs;
+
+    /**
+     * Indicates if some jump instructions are too small and need to be resized.
+     */
+    private boolean resize;
+
+    /**
+     * The number of subroutines in this method.
+     */
+    private int subroutines;
+
+    // ------------------------------------------------------------------------
+
+    /*
+     * Fields for the control flow graph analysis algorithm (used to compute the
+     * maximum stack size). A control flow graph contains one node per "basic
+     * block", and one edge per "jump" from one basic block to another. Each
+     * node (i.e., each basic block) is represented by the Label object that
+     * corresponds to the first instruction of this basic block. Each node also
+     * stores the list of its successors in the graph, as a linked list of Edge
+     * objects.
+     */
+
+    /**
+     * Indicates what must be automatically computed.
+     *
+     * @see #FRAMES
+     * @see #MAXS
+     * @see #NOTHING
+     */
+    private final int compute;
+
+    /**
+     * A list of labels. This list is the list of basic blocks in the method,
+     * i.e. a list of Label objects linked to each other by their
+     * {@link Label#successor} field, in the order they are visited by
+     * {@link MethodVisitor#visitLabel}, and starting with the first basic block.
+     */
+    private Label labels;
+
+    /**
+     * The previous basic block.
+     */
+    private Label previousBlock;
+
+    /**
+     * The current basic block.
+     */
+    private Label currentBlock;
+
+    /**
+     * The (relative) stack size after the last visited instruction. This size
+     * is relative to the beginning of the current basic block, i.e., the true
+     * stack size after the last visited instruction is equal to the
+     * {@link Label#inputStackTop beginStackSize} of the current basic block
+     * plus <tt>stackSize</tt>.
+     */
+    private int stackSize;
+
+    /**
+     * The (relative) maximum stack size after the last visited instruction.
+     * This size is relative to the beginning of the current basic block, i.e.,
+     * the true maximum stack size after the last visited instruction is equal
+     * to the {@link Label#inputStackTop beginStackSize} of the current basic
+     * block plus <tt>stackSize</tt>.
+     */
+    private int maxStackSize;
+
+    // ------------------------------------------------------------------------
+    // Constructor
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a new {@link MethodWriter}.
+     *
+     * @param cw the class writer in which the method must be added.
+     * @param access the method's access flags (see {@link Opcodes}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type}).
+     * @param signature the method's signature. May be <tt>null</tt>.
+     * @param exceptions the internal names of the method's exceptions. May be
+     *        <tt>null</tt>.
+     * @param computeMaxs <tt>true</tt> if the maximum stack size and number
+     *        of local variables must be automatically computed.
+     * @param computeFrames <tt>true</tt> if the stack map tables must be
+     *        recomputed from scratch.
+     */
+    MethodWriter(
+        final ClassWriter cw,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions,
+        final boolean computeMaxs,
+        final boolean computeFrames)
+    {
+        super(Opcodes.ASM4);
+        if (cw.firstMethod == null) {
+            cw.firstMethod = this;
+        } else {
+            cw.lastMethod.mv = this;
+        }
+        cw.lastMethod = this;
+        this.cw = cw;
+        this.access = access;
+        this.name = cw.newUTF8(name);
+        this.desc = cw.newUTF8(desc);
+        this.descriptor = desc;
+        if (ClassReader.SIGNATURES) {
+            this.signature = signature;
+        }
+        if (exceptions != null && exceptions.length > 0) {
+            exceptionCount = exceptions.length;
+            this.exceptions = new int[exceptionCount];
+            for (int i = 0; i < exceptionCount; ++i) {
+                this.exceptions[i] = cw.newClass(exceptions[i]);
+            }
+        }
+        this.compute = computeFrames ? FRAMES : (computeMaxs ? MAXS : NOTHING);
+        if (computeMaxs || computeFrames) {
+            if (computeFrames && "<init>".equals(name)) {
+                this.access |= ACC_CONSTRUCTOR;
+            }
+            // updates maxLocals
+            int size = Type.getArgumentsAndReturnSizes(descriptor) >> 2;
+            if ((access & Opcodes.ACC_STATIC) != 0) {
+                --size;
+            }
+            maxLocals = size;
+            currentLocals = size;
+            // creates and visits the label for the first basic block
+            labels = new Label();
+            labels.status |= Label.PUSHED;
+            visitLabel(labels);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the MethodVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public AnnotationVisitor visitAnnotationDefault() {
+        if (!ClassReader.ANNOTATIONS) {
+            return null;
+        }
+        annd = new ByteVector();
+        return new AnnotationWriter(cw, false, annd, null, 0);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        if (!ClassReader.ANNOTATIONS) {
+            return null;
+        }
+        ByteVector bv = new ByteVector();
+        // write type, and reserve space for values count
+        bv.putShort(cw.newUTF8(desc)).putShort(0);
+        AnnotationWriter aw = new AnnotationWriter(cw, true, bv, bv, 2);
+        if (visible) {
+            aw.next = anns;
+            anns = aw;
+        } else {
+            aw.next = ianns;
+            ianns = aw;
+        }
+        return aw;
+    }
+
+    @Override
+    public AnnotationVisitor visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible)
+    {
+        if (!ClassReader.ANNOTATIONS) {
+            return null;
+        }
+        ByteVector bv = new ByteVector();
+        if ("Ljava/lang/Synthetic;".equals(desc)) {
+            // workaround for a bug in javac with synthetic parameters
+            // see ClassReader.readParameterAnnotations
+            synthetics = Math.max(synthetics, parameter + 1);
+            return new AnnotationWriter(cw, false, bv, null, 0);
+        }
+        // write type, and reserve space for values count
+        bv.putShort(cw.newUTF8(desc)).putShort(0);
+        AnnotationWriter aw = new AnnotationWriter(cw, true, bv, bv, 2);
+        if (visible) {
+            if (panns == null) {
+                panns = new AnnotationWriter[Type.getArgumentTypes(descriptor).length];
+            }
+            aw.next = panns[parameter];
+            panns[parameter] = aw;
+        } else {
+            if (ipanns == null) {
+                ipanns = new AnnotationWriter[Type.getArgumentTypes(descriptor).length];
+            }
+            aw.next = ipanns[parameter];
+            ipanns[parameter] = aw;
+        }
+        return aw;
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        if (attr.isCodeAttribute()) {
+            attr.next = cattrs;
+            cattrs = attr;
+        } else {
+            attr.next = attrs;
+            attrs = attr;
+        }
+    }
+
+    @Override
+    public void visitCode() {
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        if (!ClassReader.FRAMES || compute == FRAMES) {
+            return;
+        }
+
+        if (type == Opcodes.F_NEW) {
+            currentLocals = nLocal;
+            startFrame(code.length, nLocal, nStack);
+            for (int i = 0; i < nLocal; ++i) {
+                if (local[i] instanceof String) {
+                    frame[frameIndex++] = Frame.OBJECT
+                            | cw.addType((String) local[i]);
+                } else if (local[i] instanceof Integer) {
+                    frame[frameIndex++] = ((Integer) local[i]).intValue();
+                } else {
+                    frame[frameIndex++] = Frame.UNINITIALIZED
+                            | cw.addUninitializedType("",
+                                    ((Label) local[i]).position);
+                }
+            }
+            for (int i = 0; i < nStack; ++i) {
+                if (stack[i] instanceof String) {
+                    frame[frameIndex++] = Frame.OBJECT
+                            | cw.addType((String) stack[i]);
+                } else if (stack[i] instanceof Integer) {
+                    frame[frameIndex++] = ((Integer) stack[i]).intValue();
+                } else {
+                    frame[frameIndex++] = Frame.UNINITIALIZED
+                            | cw.addUninitializedType("",
+                                    ((Label) stack[i]).position);
+                }
+            }
+            endFrame();
+        } else {
+            int delta;
+            if (stackMap == null) {
+                stackMap = new ByteVector();
+                delta = code.length;
+            } else {
+                delta = code.length - previousFrameOffset - 1;
+                if (delta < 0) {
+                    if (type == Opcodes.F_SAME) {
+                        return;
+                    } else {
+                        throw new IllegalStateException();
+                    }
+                }
+            }
+
+            switch (type) {
+                case Opcodes.F_FULL:
+                    currentLocals = nLocal;
+                    stackMap.putByte(FULL_FRAME)
+                            .putShort(delta)
+                            .putShort(nLocal);
+                    for (int i = 0; i < nLocal; ++i) {
+                        writeFrameType(local[i]);
+                    }
+                    stackMap.putShort(nStack);
+                    for (int i = 0; i < nStack; ++i) {
+                        writeFrameType(stack[i]);
+                    }
+                    break;
+                case Opcodes.F_APPEND:
+                    currentLocals += nLocal;
+                    stackMap.putByte(SAME_FRAME_EXTENDED + nLocal)
+                            .putShort(delta);
+                    for (int i = 0; i < nLocal; ++i) {
+                        writeFrameType(local[i]);
+                    }
+                    break;
+                case Opcodes.F_CHOP:
+                    currentLocals -= nLocal;
+                    stackMap.putByte(SAME_FRAME_EXTENDED - nLocal)
+                            .putShort(delta);
+                    break;
+                case Opcodes.F_SAME:
+                    if (delta < 64) {
+                        stackMap.putByte(delta);
+                    } else {
+                        stackMap.putByte(SAME_FRAME_EXTENDED).putShort(delta);
+                    }
+                    break;
+                case Opcodes.F_SAME1:
+                    if (delta < 64) {
+                        stackMap.putByte(SAME_LOCALS_1_STACK_ITEM_FRAME + delta);
+                    } else {
+                        stackMap.putByte(SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED)
+                                .putShort(delta);
+                    }
+                    writeFrameType(stack[0]);
+                    break;
+            }
+
+            previousFrameOffset = code.length;
+            ++frameCount;
+        }
+
+        maxStack = Math.max(maxStack, nStack);
+        maxLocals = Math.max(maxLocals, currentLocals);
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        // adds the instruction to the bytecode of the method
+        code.putByte(opcode);
+        // update currentBlock
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, 0, null, null);
+            } else {
+                // updates current and max stack sizes
+                int size = stackSize + Frame.SIZE[opcode];
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+            // if opcode == ATHROW or xRETURN, ends current block (no successor)
+            if ((opcode >= Opcodes.IRETURN && opcode <= Opcodes.RETURN)
+                    || opcode == Opcodes.ATHROW)
+            {
+                noSuccessor();
+            }
+        }
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, operand, null, null);
+            } else if (opcode != Opcodes.NEWARRAY) {
+                // updates current and max stack sizes only for NEWARRAY
+                // (stack size variation = 0 for BIPUSH or SIPUSH)
+                int size = stackSize + 1;
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        if (opcode == Opcodes.SIPUSH) {
+            code.put12(opcode, operand);
+        } else { // BIPUSH or NEWARRAY
+            code.put11(opcode, operand);
+        }
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, var, null, null);
+            } else {
+                // updates current and max stack sizes
+                if (opcode == Opcodes.RET) {
+                    // no stack change, but end of current block (no successor)
+                    currentBlock.status |= Label.RET;
+                    // save 'stackSize' here for future use
+                    // (see {@link #findSubroutineSuccessors})
+                    currentBlock.inputStackTop = stackSize;
+                    noSuccessor();
+                } else { // xLOAD or xSTORE
+                    int size = stackSize + Frame.SIZE[opcode];
+                    if (size > maxStackSize) {
+                        maxStackSize = size;
+                    }
+                    stackSize = size;
+                }
+            }
+        }
+        if (compute != NOTHING) {
+            // updates max locals
+            int n;
+            if (opcode == Opcodes.LLOAD || opcode == Opcodes.DLOAD
+                    || opcode == Opcodes.LSTORE || opcode == Opcodes.DSTORE)
+            {
+                n = var + 2;
+            } else {
+                n = var + 1;
+            }
+            if (n > maxLocals) {
+                maxLocals = n;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        if (var < 4 && opcode != Opcodes.RET) {
+            int opt;
+            if (opcode < Opcodes.ISTORE) {
+                /* ILOAD_0 */
+                opt = 26 + ((opcode - Opcodes.ILOAD) << 2) + var;
+            } else {
+                /* ISTORE_0 */
+                opt = 59 + ((opcode - Opcodes.ISTORE) << 2) + var;
+            }
+            code.putByte(opt);
+        } else if (var >= 256) {
+            code.putByte(196 /* WIDE */).put12(opcode, var);
+        } else {
+            code.put11(opcode, var);
+        }
+        if (opcode >= Opcodes.ISTORE && compute == FRAMES && handlerCount > 0) {
+            visitLabel(new Label());
+        }
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        Item i = cw.newClassItem(type);
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, code.length, cw, i);
+            } else if (opcode == Opcodes.NEW) {
+                // updates current and max stack sizes only if opcode == NEW
+                // (no stack change for ANEWARRAY, CHECKCAST, INSTANCEOF)
+                int size = stackSize + 1;
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        code.put12(opcode, i.index);
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        Item i = cw.newFieldItem(owner, name, desc);
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, 0, cw, i);
+            } else {
+                int size;
+                // computes the stack size variation
+                char c = desc.charAt(0);
+                switch (opcode) {
+                    case Opcodes.GETSTATIC:
+                        size = stackSize + (c == 'D' || c == 'J' ? 2 : 1);
+                        break;
+                    case Opcodes.PUTSTATIC:
+                        size = stackSize + (c == 'D' || c == 'J' ? -2 : -1);
+                        break;
+                    case Opcodes.GETFIELD:
+                        size = stackSize + (c == 'D' || c == 'J' ? 1 : 0);
+                        break;
+                    // case Constants.PUTFIELD:
+                    default:
+                        size = stackSize + (c == 'D' || c == 'J' ? -3 : -2);
+                        break;
+                }
+                // updates current and max stack sizes
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        code.put12(opcode, i.index);
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        boolean itf = opcode == Opcodes.INVOKEINTERFACE;
+        Item i = cw.newMethodItem(owner, name, desc, itf);
+        int argSize = i.intVal;
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, 0, cw, i);
+            } else {
+                /*
+                 * computes the stack size variation. In order not to recompute
+                 * several times this variation for the same Item, we use the
+                 * intVal field of this item to store this variation, once it
+                 * has been computed. More precisely this intVal field stores
+                 * the sizes of the arguments and of the return value
+                 * corresponding to desc.
+                 */
+                if (argSize == 0) {
+                    // the above sizes have not been computed yet,
+                    // so we compute them...
+                    argSize = Type.getArgumentsAndReturnSizes(desc);
+                    // ... and we save them in order
+                    // not to recompute them in the future
+                    i.intVal = argSize;
+                }
+                int size;
+                if (opcode == Opcodes.INVOKESTATIC) {
+                    size = stackSize - (argSize >> 2) + (argSize & 0x03) + 1;
+                } else {
+                    size = stackSize - (argSize >> 2) + (argSize & 0x03);
+                }
+                // updates current and max stack sizes
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        if (itf) {
+            if (argSize == 0) {
+                argSize = Type.getArgumentsAndReturnSizes(desc);
+                i.intVal = argSize;
+            }
+            code.put12(Opcodes.INVOKEINTERFACE, i.index).put11(argSize >> 2, 0);
+        } else {
+            code.put12(opcode, i.index);
+        }
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        final String name,
+        final String desc,
+        final Handle bsm,
+        final Object... bsmArgs)
+    {
+        Item i = cw.newInvokeDynamicItem(name, desc, bsm, bsmArgs);
+        int argSize = i.intVal;
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(Opcodes.INVOKEDYNAMIC, 0, cw, i);
+            } else {
+                /*
+                 * computes the stack size variation. In order not to recompute
+                 * several times this variation for the same Item, we use the
+                 * intVal field of this item to store this variation, once it
+                 * has been computed. More precisely this intVal field stores
+                 * the sizes of the arguments and of the return value
+                 * corresponding to desc.
+                 */
+                if (argSize == 0) {
+                    // the above sizes have not been computed yet,
+                    // so we compute them...
+                    argSize = Type.getArgumentsAndReturnSizes(desc);
+                    // ... and we save them in order
+                    // not to recompute them in the future
+                    i.intVal = argSize;
+                }
+                int size = stackSize - (argSize >> 2) + (argSize & 0x03) + 1;
+
+                // updates current and max stack sizes
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        code.put12(Opcodes.INVOKEDYNAMIC, i.index);
+        code.putShort(0);
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        Label nextInsn = null;
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(opcode, 0, null, null);
+                // 'label' is the target of a jump instruction
+                label.getFirst().status |= Label.TARGET;
+                // adds 'label' as a successor of this basic block
+                addSuccessor(Edge.NORMAL, label);
+                if (opcode != Opcodes.GOTO) {
+                    // creates a Label for the next basic block
+                    nextInsn = new Label();
+                }
+            } else {
+                if (opcode == Opcodes.JSR) {
+                    if ((label.status & Label.SUBROUTINE) == 0) {
+                        label.status |= Label.SUBROUTINE;
+                        ++subroutines;
+                    }
+                    currentBlock.status |= Label.JSR;
+                    addSuccessor(stackSize + 1, label);
+                    // creates a Label for the next basic block
+                    nextInsn = new Label();
+                    /*
+                     * note that, by construction in this method, a JSR block
+                     * has at least two successors in the control flow graph:
+                     * the first one leads the next instruction after the JSR,
+                     * while the second one leads to the JSR target.
+                     */
+                } else {
+                    // updates current stack size (max stack size unchanged
+                    // because stack size variation always negative in this
+                    // case)
+                    stackSize += Frame.SIZE[opcode];
+                    addSuccessor(stackSize, label);
+                }
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        if ((label.status & Label.RESOLVED) != 0
+                && label.position - code.length < Short.MIN_VALUE)
+        {
+            /*
+             * case of a backward jump with an offset < -32768. In this case we
+             * automatically replace GOTO with GOTO_W, JSR with JSR_W and IFxxx
+             * <l> with IFNOTxxx <l'> GOTO_W <l>, where IFNOTxxx is the
+             * "opposite" opcode of IFxxx (i.e., IFNE for IFEQ) and where <l'>
+             * designates the instruction just after the GOTO_W.
+             */
+            if (opcode == Opcodes.GOTO) {
+                code.putByte(200); // GOTO_W
+            } else if (opcode == Opcodes.JSR) {
+                code.putByte(201); // JSR_W
+            } else {
+                // if the IF instruction is transformed into IFNOT GOTO_W the
+                // next instruction becomes the target of the IFNOT instruction
+                if (nextInsn != null) {
+                    nextInsn.status |= Label.TARGET;
+                }
+                code.putByte(opcode <= 166
+                        ? ((opcode + 1) ^ 1) - 1
+                        : opcode ^ 1);
+                code.putShort(8); // jump offset
+                code.putByte(200); // GOTO_W
+            }
+            label.put(this, code, code.length - 1, true);
+        } else {
+            /*
+             * case of a backward jump with an offset >= -32768, or of a forward
+             * jump with, of course, an unknown offset. In these cases we store
+             * the offset in 2 bytes (which will be increased in
+             * resizeInstructions, if needed).
+             */
+            code.putByte(opcode);
+            label.put(this, code, code.length - 1, false);
+        }
+        if (currentBlock != null) {
+            if (nextInsn != null) {
+                // if the jump instruction is not a GOTO, the next instruction
+                // is also a successor of this instruction. Calling visitLabel
+                // adds the label of this next instruction as a successor of the
+                // current block, and starts a new basic block
+                visitLabel(nextInsn);
+            }
+            if (opcode == Opcodes.GOTO) {
+                noSuccessor();
+            }
+        }
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        // resolves previous forward references to label, if any
+        resize |= label.resolve(this, code.length, code.data);
+        // updates currentBlock
+        if ((label.status & Label.DEBUG) != 0) {
+            return;
+        }
+        if (compute == FRAMES) {
+            if (currentBlock != null) {
+                if (label.position == currentBlock.position) {
+                    // successive labels, do not start a new basic block
+                    currentBlock.status |= (label.status & Label.TARGET);
+                    label.frame = currentBlock.frame;
+                    return;
+                }
+                // ends current block (with one new successor)
+                addSuccessor(Edge.NORMAL, label);
+            }
+            // begins a new current block
+            currentBlock = label;
+            if (label.frame == null) {
+                label.frame = new Frame();
+                label.frame.owner = label;
+            }
+            // updates the basic block list
+            if (previousBlock != null) {
+                if (label.position == previousBlock.position) {
+                    previousBlock.status |= (label.status & Label.TARGET);
+                    label.frame = previousBlock.frame;
+                    currentBlock = previousBlock;
+                    return;
+                }
+                previousBlock.successor = label;
+            }
+            previousBlock = label;
+        } else if (compute == MAXS) {
+            if (currentBlock != null) {
+                // ends current block (with one new successor)
+                currentBlock.outputStackMax = maxStackSize;
+                addSuccessor(stackSize, label);
+            }
+            // begins a new current block
+            currentBlock = label;
+            // resets the relative current and max stack sizes
+            stackSize = 0;
+            maxStackSize = 0;
+            // updates the basic block list
+            if (previousBlock != null) {
+                previousBlock.successor = label;
+            }
+            previousBlock = label;
+        }
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        Item i = cw.newConstItem(cst);
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(Opcodes.LDC, 0, cw, i);
+            } else {
+                int size;
+                // computes the stack size variation
+                if (i.type == ClassWriter.LONG || i.type == ClassWriter.DOUBLE)
+                {
+                    size = stackSize + 2;
+                } else {
+                    size = stackSize + 1;
+                }
+                // updates current and max stack sizes
+                if (size > maxStackSize) {
+                    maxStackSize = size;
+                }
+                stackSize = size;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        int index = i.index;
+        if (i.type == ClassWriter.LONG || i.type == ClassWriter.DOUBLE) {
+            code.put12(20 /* LDC2_W */, index);
+        } else if (index >= 256) {
+            code.put12(19 /* LDC_W */, index);
+        } else {
+            code.put11(Opcodes.LDC, index);
+        }
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(Opcodes.IINC, var, null, null);
+            }
+        }
+        if (compute != NOTHING) {
+            // updates max locals
+            int n = var + 1;
+            if (n > maxLocals) {
+                maxLocals = n;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        if ((var > 255) || (increment > 127) || (increment < -128)) {
+            code.putByte(196 /* WIDE */)
+                    .put12(Opcodes.IINC, var)
+                    .putShort(increment);
+        } else {
+            code.putByte(Opcodes.IINC).put11(var, increment);
+        }
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        // adds the instruction to the bytecode of the method
+        int source = code.length;
+        code.putByte(Opcodes.TABLESWITCH);
+        code.putByteArray(null, 0, (4 - code.length % 4) % 4);
+        dflt.put(this, code, source, true);
+        code.putInt(min).putInt(max);
+        for (int i = 0; i < labels.length; ++i) {
+            labels[i].put(this, code, source, true);
+        }
+        // updates currentBlock
+        visitSwitchInsn(dflt, labels);
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        // adds the instruction to the bytecode of the method
+        int source = code.length;
+        code.putByte(Opcodes.LOOKUPSWITCH);
+        code.putByteArray(null, 0, (4 - code.length % 4) % 4);
+        dflt.put(this, code, source, true);
+        code.putInt(labels.length);
+        for (int i = 0; i < labels.length; ++i) {
+            code.putInt(keys[i]);
+            labels[i].put(this, code, source, true);
+        }
+        // updates currentBlock
+        visitSwitchInsn(dflt, labels);
+    }
+
+    private void visitSwitchInsn(final Label dflt, final Label[] labels) {
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(Opcodes.LOOKUPSWITCH, 0, null, null);
+                // adds current block successors
+                addSuccessor(Edge.NORMAL, dflt);
+                dflt.getFirst().status |= Label.TARGET;
+                for (int i = 0; i < labels.length; ++i) {
+                    addSuccessor(Edge.NORMAL, labels[i]);
+                    labels[i].getFirst().status |= Label.TARGET;
+                }
+            } else {
+                // updates current stack size (max stack size unchanged)
+                --stackSize;
+                // adds current block successors
+                addSuccessor(stackSize, dflt);
+                for (int i = 0; i < labels.length; ++i) {
+                    addSuccessor(stackSize, labels[i]);
+                }
+            }
+            // ends current block
+            noSuccessor();
+        }
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        Item i = cw.newClassItem(desc);
+        // Label currentBlock = this.currentBlock;
+        if (currentBlock != null) {
+            if (compute == FRAMES) {
+                currentBlock.frame.execute(Opcodes.MULTIANEWARRAY, dims, cw, i);
+            } else {
+                // updates current stack size (max stack size unchanged because
+                // stack size variation always negative or null)
+                stackSize += 1 - dims;
+            }
+        }
+        // adds the instruction to the bytecode of the method
+        code.put12(Opcodes.MULTIANEWARRAY, i.index).putByte(dims);
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type)
+    {
+        ++handlerCount;
+        Handler h = new Handler();
+        h.start = start;
+        h.end = end;
+        h.handler = handler;
+        h.desc = type;
+        h.type = type != null ? cw.newClass(type) : 0;
+        if (lastHandler == null) {
+            firstHandler = h;
+        } else {
+            lastHandler.next = h;
+        }
+        lastHandler = h;
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        if (signature != null) {
+            if (localVarType == null) {
+                localVarType = new ByteVector();
+            }
+            ++localVarTypeCount;
+            localVarType.putShort(start.position)
+                    .putShort(end.position - start.position)
+                    .putShort(cw.newUTF8(name))
+                    .putShort(cw.newUTF8(signature))
+                    .putShort(index);
+        }
+        if (localVar == null) {
+            localVar = new ByteVector();
+        }
+        ++localVarCount;
+        localVar.putShort(start.position)
+                .putShort(end.position - start.position)
+                .putShort(cw.newUTF8(name))
+                .putShort(cw.newUTF8(desc))
+                .putShort(index);
+        if (compute != NOTHING) {
+            // updates max locals
+            char c = desc.charAt(0);
+            int n = index + (c == 'J' || c == 'D' ? 2 : 1);
+            if (n > maxLocals) {
+                maxLocals = n;
+            }
+        }
+    }
+
+    @Override
+    public void visitLineNumber(final int line, final Label start) {
+        if (lineNumber == null) {
+            lineNumber = new ByteVector();
+        }
+        ++lineNumberCount;
+        lineNumber.putShort(start.position);
+        lineNumber.putShort(line);
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        if (ClassReader.FRAMES && compute == FRAMES) {
+            // completes the control flow graph with exception handler blocks
+            Handler handler = firstHandler;
+            while (handler != null) {
+                Label l = handler.start.getFirst();
+                Label h = handler.handler.getFirst();
+                Label e = handler.end.getFirst();
+                // computes the kind of the edges to 'h'
+                String t = handler.desc == null
+                        ? "java/lang/Throwable"
+                        : handler.desc;
+                int kind = Frame.OBJECT | cw.addType(t);
+                // h is an exception handler
+                h.status |= Label.TARGET;
+                // adds 'h' as a successor of labels between 'start' and 'end'
+                while (l != e) {
+                    // creates an edge to 'h'
+                    Edge b = new Edge();
+                    b.info = kind;
+                    b.successor = h;
+                    // adds it to the successors of 'l'
+                    b.next = l.successors;
+                    l.successors = b;
+                    // goes to the next label
+                    l = l.successor;
+                }
+                handler = handler.next;
+            }
+
+            // creates and visits the first (implicit) frame
+            Frame f = labels.frame;
+            Type[] args = Type.getArgumentTypes(descriptor);
+            f.initInputFrame(cw, access, args, this.maxLocals);
+            visitFrame(f);
+
+            /*
+             * fix point algorithm: mark the first basic block as 'changed'
+             * (i.e. put it in the 'changed' list) and, while there are changed
+             * basic blocks, choose one, mark it as unchanged, and update its
+             * successors (which can be changed in the process).
+             */
+            int max = 0;
+            Label changed = labels;
+            while (changed != null) {
+                // removes a basic block from the list of changed basic blocks
+                Label l = changed;
+                changed = changed.next;
+                l.next = null;
+                f = l.frame;
+                // a reachable jump target must be stored in the stack map
+                if ((l.status & Label.TARGET) != 0) {
+                    l.status |= Label.STORE;
+                }
+                // all visited labels are reachable, by definition
+                l.status |= Label.REACHABLE;
+                // updates the (absolute) maximum stack size
+                int blockMax = f.inputStack.length + l.outputStackMax;
+                if (blockMax > max) {
+                    max = blockMax;
+                }
+                // updates the successors of the current basic block
+                Edge e = l.successors;
+                while (e != null) {
+                    Label n = e.successor.getFirst();
+                    boolean change = f.merge(cw, n.frame, e.info);
+                    if (change && n.next == null) {
+                        // if n has changed and is not already in the 'changed'
+                        // list, adds it to this list
+                        n.next = changed;
+                        changed = n;
+                    }
+                    e = e.next;
+                }
+            }
+
+            // visits all the frames that must be stored in the stack map
+            Label l = labels;
+            while (l != null) {
+                f = l.frame;
+                if ((l.status & Label.STORE) != 0) {
+                    visitFrame(f);
+                }
+                if ((l.status & Label.REACHABLE) == 0) {
+                    // finds start and end of dead basic block
+                    Label k = l.successor;
+                    int start = l.position;
+                    int end = (k == null ? code.length : k.position) - 1;
+                    // if non empty basic block
+                    if (end >= start) {
+                        max = Math.max(max, 1);
+                        // replaces instructions with NOP ... NOP ATHROW
+                        for (int i = start; i < end; ++i) {
+                            code.data[i] = Opcodes.NOP;
+                        }
+                        code.data[end] = (byte) Opcodes.ATHROW;
+                        // emits a frame for this unreachable block
+                        startFrame(start, 0, 1);
+                        frame[frameIndex++] = Frame.OBJECT
+                                | cw.addType("java/lang/Throwable");
+                        endFrame();
+                        // removes the start-end range from the exception handlers
+                        firstHandler = Handler.remove(firstHandler, l, k);
+                    }
+                }
+                l = l.successor;
+            }
+
+            handler = firstHandler;
+            handlerCount = 0;
+            while (handler != null) {
+                handlerCount += 1;
+                handler = handler.next;
+            }
+
+            this.maxStack = max;
+        } else if (compute == MAXS) {
+            // completes the control flow graph with exception handler blocks
+            Handler handler = firstHandler;
+            while (handler != null) {
+                Label l = handler.start;
+                Label h = handler.handler;
+                Label e = handler.end;
+                // adds 'h' as a successor of labels between 'start' and 'end'
+                while (l != e) {
+                    // creates an edge to 'h'
+                    Edge b = new Edge();
+                    b.info = Edge.EXCEPTION;
+                    b.successor = h;
+                    // adds it to the successors of 'l'
+                    if ((l.status & Label.JSR) == 0) {
+                        b.next = l.successors;
+                        l.successors = b;
+                    } else {
+                        // if l is a JSR block, adds b after the first two edges
+                        // to preserve the hypothesis about JSR block successors
+                        // order (see {@link #visitJumpInsn})
+                        b.next = l.successors.next.next;
+                        l.successors.next.next = b;
+                    }
+                    // goes to the next label
+                    l = l.successor;
+                }
+                handler = handler.next;
+            }
+
+            if (subroutines > 0) {
+                // completes the control flow graph with the RET successors
+                /*
+                 * first step: finds the subroutines. This step determines, for
+                 * each basic block, to which subroutine(s) it belongs.
+                 */
+                // finds the basic blocks that belong to the "main" subroutine
+                int id = 0;
+                labels.visitSubroutine(null, 1, subroutines);
+                // finds the basic blocks that belong to the real subroutines
+                Label l = labels;
+                while (l != null) {
+                    if ((l.status & Label.JSR) != 0) {
+                        // the subroutine is defined by l's TARGET, not by l
+                        Label subroutine = l.successors.next.successor;
+                        // if this subroutine has not been visited yet...
+                        if ((subroutine.status & Label.VISITED) == 0) {
+                            // ...assigns it a new id and finds its basic blocks
+                            id += 1;
+                            subroutine.visitSubroutine(null, (id / 32L) << 32
+                                    | (1L << (id % 32)), subroutines);
+                        }
+                    }
+                    l = l.successor;
+                }
+                // second step: finds the successors of RET blocks
+                l = labels;
+                while (l != null) {
+                    if ((l.status & Label.JSR) != 0) {
+                        Label L = labels;
+                        while (L != null) {
+                            L.status &= ~Label.VISITED2;
+                            L = L.successor;
+                        }
+                        // the subroutine is defined by l's TARGET, not by l
+                        Label subroutine = l.successors.next.successor;
+                        subroutine.visitSubroutine(l, 0, subroutines);
+                    }
+                    l = l.successor;
+                }
+            }
+
+            /*
+             * control flow analysis algorithm: while the block stack is not
+             * empty, pop a block from this stack, update the max stack size,
+             * compute the true (non relative) begin stack size of the
+             * successors of this block, and push these successors onto the
+             * stack (unless they have already been pushed onto the stack).
+             * Note: by hypothesis, the {@link Label#inputStackTop} of the
+             * blocks in the block stack are the true (non relative) beginning
+             * stack sizes of these blocks.
+             */
+            int max = 0;
+            Label stack = labels;
+            while (stack != null) {
+                // pops a block from the stack
+                Label l = stack;
+                stack = stack.next;
+                // computes the true (non relative) max stack size of this block
+                int start = l.inputStackTop;
+                int blockMax = start + l.outputStackMax;
+                // updates the global max stack size
+                if (blockMax > max) {
+                    max = blockMax;
+                }
+                // analyzes the successors of the block
+                Edge b = l.successors;
+                if ((l.status & Label.JSR) != 0) {
+                    // ignores the first edge of JSR blocks (virtual successor)
+                    b = b.next;
+                }
+                while (b != null) {
+                    l = b.successor;
+                    // if this successor has not already been pushed...
+                    if ((l.status & Label.PUSHED) == 0) {
+                        // computes its true beginning stack size...
+                        l.inputStackTop = b.info == Edge.EXCEPTION ? 1 : start
+                                + b.info;
+                        // ...and pushes it onto the stack
+                        l.status |= Label.PUSHED;
+                        l.next = stack;
+                        stack = l;
+                    }
+                    b = b.next;
+                }
+            }
+            this.maxStack = Math.max(maxStack, max);
+        } else {
+            this.maxStack = maxStack;
+            this.maxLocals = maxLocals;
+        }
+    }
+
+    @Override
+    public void visitEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods: control flow analysis algorithm
+    // ------------------------------------------------------------------------
+
+    /**
+     * Adds a successor to the {@link #currentBlock currentBlock} block.
+     *
+     * @param info information about the control flow edge to be added.
+     * @param successor the successor block to be added to the current block.
+     */
+    private void addSuccessor(final int info, final Label successor) {
+        // creates and initializes an Edge object...
+        Edge b = new Edge();
+        b.info = info;
+        b.successor = successor;
+        // ...and adds it to the successor list of the currentBlock block
+        b.next = currentBlock.successors;
+        currentBlock.successors = b;
+    }
+
+    /**
+     * Ends the current basic block. This method must be used in the case where
+     * the current basic block does not have any successor.
+     */
+    private void noSuccessor() {
+        if (compute == FRAMES) {
+            Label l = new Label();
+            l.frame = new Frame();
+            l.frame.owner = l;
+            l.resolve(this, code.length, code.data);
+            previousBlock.successor = l;
+            previousBlock = l;
+        } else {
+            currentBlock.outputStackMax = maxStackSize;
+        }
+        currentBlock = null;
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods: stack map frames
+    // ------------------------------------------------------------------------
+
+    /**
+     * Visits a frame that has been computed from scratch.
+     *
+     * @param f the frame that must be visited.
+     */
+    private void visitFrame(final Frame f) {
+        int i, t;
+        int nTop = 0;
+        int nLocal = 0;
+        int nStack = 0;
+        int[] locals = f.inputLocals;
+        int[] stacks = f.inputStack;
+        // computes the number of locals (ignores TOP types that are just after
+        // a LONG or a DOUBLE, and all trailing TOP types)
+        for (i = 0; i < locals.length; ++i) {
+            t = locals[i];
+            if (t == Frame.TOP) {
+                ++nTop;
+            } else {
+                nLocal += nTop + 1;
+                nTop = 0;
+            }
+            if (t == Frame.LONG || t == Frame.DOUBLE) {
+                ++i;
+            }
+        }
+        // computes the stack size (ignores TOP types that are just after
+        // a LONG or a DOUBLE)
+        for (i = 0; i < stacks.length; ++i) {
+            t = stacks[i];
+            ++nStack;
+            if (t == Frame.LONG || t == Frame.DOUBLE) {
+                ++i;
+            }
+        }
+        // visits the frame and its content
+        startFrame(f.owner.position, nLocal, nStack);
+        for (i = 0; nLocal > 0; ++i, --nLocal) {
+            t = locals[i];
+            frame[frameIndex++] = t;
+            if (t == Frame.LONG || t == Frame.DOUBLE) {
+                ++i;
+            }
+        }
+        for (i = 0; i < stacks.length; ++i) {
+            t = stacks[i];
+            frame[frameIndex++] = t;
+            if (t == Frame.LONG || t == Frame.DOUBLE) {
+                ++i;
+            }
+        }
+        endFrame();
+    }
+
+    /**
+     * Starts the visit of a stack map frame.
+     *
+     * @param offset the offset of the instruction to which the frame
+     *        corresponds.
+     * @param nLocal the number of local variables in the frame.
+     * @param nStack the number of stack elements in the frame.
+     */
+    private void startFrame(final int offset, final int nLocal, final int nStack)
+    {
+        int n = 3 + nLocal + nStack;
+        if (frame == null || frame.length < n) {
+            frame = new int[n];
+        }
+        frame[0] = offset;
+        frame[1] = nLocal;
+        frame[2] = nStack;
+        frameIndex = 3;
+    }
+
+    /**
+     * Checks if the visit of the current frame {@link #frame} is finished, and
+     * if yes, write it in the StackMapTable attribute.
+     */
+    private void endFrame() {
+        if (previousFrame != null) { // do not write the first frame
+            if (stackMap == null) {
+                stackMap = new ByteVector();
+            }
+            writeFrame();
+            ++frameCount;
+        }
+        previousFrame = frame;
+        frame = null;
+    }
+
+    /**
+     * Compress and writes the current frame {@link #frame} in the StackMapTable
+     * attribute.
+     */
+    private void writeFrame() {
+        int clocalsSize = frame[1];
+        int cstackSize = frame[2];
+        if ((cw.version & 0xFFFF) < Opcodes.V1_6) {
+            stackMap.putShort(frame[0]).putShort(clocalsSize);
+            writeFrameTypes(3, 3 + clocalsSize);
+            stackMap.putShort(cstackSize);
+            writeFrameTypes(3 + clocalsSize, 3 + clocalsSize + cstackSize);
+            return;
+        }
+        int localsSize = previousFrame[1];
+        int type = FULL_FRAME;
+        int k = 0;
+        int delta;
+        if (frameCount == 0) {
+            delta = frame[0];
+        } else {
+            delta = frame[0] - previousFrame[0] - 1;
+        }
+        if (cstackSize == 0) {
+            k = clocalsSize - localsSize;
+            switch (k) {
+                case -3:
+                case -2:
+                case -1:
+                    type = CHOP_FRAME;
+                    localsSize = clocalsSize;
+                    break;
+                case 0:
+                    type = delta < 64 ? SAME_FRAME : SAME_FRAME_EXTENDED;
+                    break;
+                case 1:
+                case 2:
+                case 3:
+                    type = APPEND_FRAME;
+                    break;
+            }
+        } else if (clocalsSize == localsSize && cstackSize == 1) {
+            type = delta < 63
+                    ? SAME_LOCALS_1_STACK_ITEM_FRAME
+                    : SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED;
+        }
+        if (type != FULL_FRAME) {
+            // verify if locals are the same
+            int l = 3;
+            for (int j = 0; j < localsSize; j++) {
+                if (frame[l] != previousFrame[l]) {
+                    type = FULL_FRAME;
+                    break;
+                }
+                l++;
+            }
+        }
+        switch (type) {
+            case SAME_FRAME:
+                stackMap.putByte(delta);
+                break;
+            case SAME_LOCALS_1_STACK_ITEM_FRAME:
+                stackMap.putByte(SAME_LOCALS_1_STACK_ITEM_FRAME + delta);
+                writeFrameTypes(3 + clocalsSize, 4 + clocalsSize);
+                break;
+            case SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED:
+                stackMap.putByte(SAME_LOCALS_1_STACK_ITEM_FRAME_EXTENDED)
+                        .putShort(delta);
+                writeFrameTypes(3 + clocalsSize, 4 + clocalsSize);
+                break;
+            case SAME_FRAME_EXTENDED:
+                stackMap.putByte(SAME_FRAME_EXTENDED).putShort(delta);
+                break;
+            case CHOP_FRAME:
+                stackMap.putByte(SAME_FRAME_EXTENDED + k).putShort(delta);
+                break;
+            case APPEND_FRAME:
+                stackMap.putByte(SAME_FRAME_EXTENDED + k).putShort(delta);
+                writeFrameTypes(3 + localsSize, 3 + clocalsSize);
+                break;
+            // case FULL_FRAME:
+            default:
+                stackMap.putByte(FULL_FRAME)
+                        .putShort(delta)
+                        .putShort(clocalsSize);
+                writeFrameTypes(3, 3 + clocalsSize);
+                stackMap.putShort(cstackSize);
+                writeFrameTypes(3 + clocalsSize, 3 + clocalsSize + cstackSize);
+        }
+    }
+
+    /**
+     * Writes some types of the current frame {@link #frame} into the
+     * StackMapTableAttribute. This method converts types from the format used
+     * in {@link Label} to the format used in StackMapTable attributes. In
+     * particular, it converts type table indexes to constant pool indexes.
+     *
+     * @param start index of the first type in {@link #frame} to write.
+     * @param end index of last type in {@link #frame} to write (exclusive).
+     */
+    private void writeFrameTypes(final int start, final int end) {
+        for (int i = start; i < end; ++i) {
+            int t = frame[i];
+            int d = t & Frame.DIM;
+            if (d == 0) {
+                int v = t & Frame.BASE_VALUE;
+                switch (t & Frame.BASE_KIND) {
+                    case Frame.OBJECT:
+                        stackMap.putByte(7)
+                                .putShort(cw.newClass(cw.typeTable[v].strVal1));
+                        break;
+                    case Frame.UNINITIALIZED:
+                        stackMap.putByte(8).putShort(cw.typeTable[v].intVal);
+                        break;
+                    default:
+                        stackMap.putByte(v);
+                }
+            } else {
+                StringBuffer buf = new StringBuffer();
+                d >>= 28;
+                while (d-- > 0) {
+                    buf.append('[');
+                }
+                if ((t & Frame.BASE_KIND) == Frame.OBJECT) {
+                    buf.append('L');
+                    buf.append(cw.typeTable[t & Frame.BASE_VALUE].strVal1);
+                    buf.append(';');
+                } else {
+                    switch (t & 0xF) {
+                        case 1:
+                            buf.append('I');
+                            break;
+                        case 2:
+                            buf.append('F');
+                            break;
+                        case 3:
+                            buf.append('D');
+                            break;
+                        case 9:
+                            buf.append('Z');
+                            break;
+                        case 10:
+                            buf.append('B');
+                            break;
+                        case 11:
+                            buf.append('C');
+                            break;
+                        case 12:
+                            buf.append('S');
+                            break;
+                        default:
+                            buf.append('J');
+                    }
+                }
+                stackMap.putByte(7).putShort(cw.newClass(buf.toString()));
+            }
+        }
+    }
+
+    private void writeFrameType(final Object type) {
+        if (type instanceof String) {
+            stackMap.putByte(7).putShort(cw.newClass((String) type));
+        } else if (type instanceof Integer) {
+            stackMap.putByte(((Integer) type).intValue());
+        } else {
+            stackMap.putByte(8).putShort(((Label) type).position);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods: dump bytecode array
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the size of the bytecode of this method.
+     *
+     * @return the size of the bytecode of this method.
+     */
+    final int getSize() {
+        if (classReaderOffset != 0) {
+            return 6 + classReaderLength;
+        }
+        if (resize) {
+            // replaces the temporary jump opcodes introduced by Label.resolve.
+            if (ClassReader.RESIZE) {
+                resizeInstructions();
+            } else {
+                throw new RuntimeException("Method code too large!");
+            }
+        }
+        int size = 8;
+        if (code.length > 0) {
+            if (code.length > 65536) {
+                throw new RuntimeException("Method code too large!");
+            }
+            cw.newUTF8("Code");
+            size += 18 + code.length + 8 * handlerCount;
+            if (localVar != null) {
+                cw.newUTF8("LocalVariableTable");
+                size += 8 + localVar.length;
+            }
+            if (localVarType != null) {
+                cw.newUTF8("LocalVariableTypeTable");
+                size += 8 + localVarType.length;
+            }
+            if (lineNumber != null) {
+                cw.newUTF8("LineNumberTable");
+                size += 8 + lineNumber.length;
+            }
+            if (stackMap != null) {
+                boolean zip = (cw.version & 0xFFFF) >= Opcodes.V1_6;
+                cw.newUTF8(zip ? "StackMapTable" : "StackMap");
+                size += 8 + stackMap.length;
+            }
+            if (cattrs != null) {
+                size += cattrs.getSize(cw,
+                        code.data,
+                        code.length,
+                        maxStack,
+                        maxLocals);
+            }
+        }
+        if (exceptionCount > 0) {
+            cw.newUTF8("Exceptions");
+            size += 8 + 2 * exceptionCount;
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((cw.version & 0xFFFF) < Opcodes.V1_5 || (access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            cw.newUTF8("Synthetic");
+            size += 6;
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            cw.newUTF8("Deprecated");
+            size += 6;
+        }
+        if (ClassReader.SIGNATURES && signature != null) {
+            cw.newUTF8("Signature");
+            cw.newUTF8(signature);
+            size += 8;
+        }
+        if (ClassReader.ANNOTATIONS && annd != null) {
+            cw.newUTF8("AnnotationDefault");
+            size += 6 + annd.length;
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            cw.newUTF8("RuntimeVisibleAnnotations");
+            size += 8 + anns.getSize();
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            cw.newUTF8("RuntimeInvisibleAnnotations");
+            size += 8 + ianns.getSize();
+        }
+        if (ClassReader.ANNOTATIONS && panns != null) {
+            cw.newUTF8("RuntimeVisibleParameterAnnotations");
+            size += 7 + 2 * (panns.length - synthetics);
+            for (int i = panns.length - 1; i >= synthetics; --i) {
+                size += panns[i] == null ? 0 : panns[i].getSize();
+            }
+        }
+        if (ClassReader.ANNOTATIONS && ipanns != null) {
+            cw.newUTF8("RuntimeInvisibleParameterAnnotations");
+            size += 7 + 2 * (ipanns.length - synthetics);
+            for (int i = ipanns.length - 1; i >= synthetics; --i) {
+                size += ipanns[i] == null ? 0 : ipanns[i].getSize();
+            }
+        }
+        if (attrs != null) {
+            size += attrs.getSize(cw, null, 0, -1, -1);
+        }
+        return size;
+    }
+
+    /**
+     * Puts the bytecode of this method in the given byte vector.
+     *
+     * @param out the byte vector into which the bytecode of this method must be
+     *        copied.
+     */
+    final void put(final ByteVector out) {
+        int mask = Opcodes.ACC_DEPRECATED
+                | ClassWriter.ACC_SYNTHETIC_ATTRIBUTE
+                | ((access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) / (ClassWriter.ACC_SYNTHETIC_ATTRIBUTE / Opcodes.ACC_SYNTHETIC));
+        out.putShort(access & ~mask).putShort(name).putShort(desc);
+        if (classReaderOffset != 0) {
+            out.putByteArray(cw.cr.b, classReaderOffset, classReaderLength);
+            return;
+        }
+        int attributeCount = 0;
+        if (code.length > 0) {
+            ++attributeCount;
+        }
+        if (exceptionCount > 0) {
+            ++attributeCount;
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((cw.version & 0xFFFF) < Opcodes.V1_5 || (access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            ++attributeCount;
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            ++attributeCount;
+        }
+        if (ClassReader.SIGNATURES && signature != null) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && annd != null) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && panns != null) {
+            ++attributeCount;
+        }
+        if (ClassReader.ANNOTATIONS && ipanns != null) {
+            ++attributeCount;
+        }
+        if (attrs != null) {
+            attributeCount += attrs.getCount();
+        }
+        out.putShort(attributeCount);
+        if (code.length > 0) {
+            int size = 12 + code.length + 8 * handlerCount;
+            if (localVar != null) {
+                size += 8 + localVar.length;
+            }
+            if (localVarType != null) {
+                size += 8 + localVarType.length;
+            }
+            if (lineNumber != null) {
+                size += 8 + lineNumber.length;
+            }
+            if (stackMap != null) {
+                size += 8 + stackMap.length;
+            }
+            if (cattrs != null) {
+                size += cattrs.getSize(cw,
+                        code.data,
+                        code.length,
+                        maxStack,
+                        maxLocals);
+            }
+            out.putShort(cw.newUTF8("Code")).putInt(size);
+            out.putShort(maxStack).putShort(maxLocals);
+            out.putInt(code.length).putByteArray(code.data, 0, code.length);
+            out.putShort(handlerCount);
+            if (handlerCount > 0) {
+                Handler h = firstHandler;
+                while (h != null) {
+                    out.putShort(h.start.position)
+                            .putShort(h.end.position)
+                            .putShort(h.handler.position)
+                            .putShort(h.type);
+                    h = h.next;
+                }
+            }
+            attributeCount = 0;
+            if (localVar != null) {
+                ++attributeCount;
+            }
+            if (localVarType != null) {
+                ++attributeCount;
+            }
+            if (lineNumber != null) {
+                ++attributeCount;
+            }
+            if (stackMap != null) {
+                ++attributeCount;
+            }
+            if (cattrs != null) {
+                attributeCount += cattrs.getCount();
+            }
+            out.putShort(attributeCount);
+            if (localVar != null) {
+                out.putShort(cw.newUTF8("LocalVariableTable"));
+                out.putInt(localVar.length + 2).putShort(localVarCount);
+                out.putByteArray(localVar.data, 0, localVar.length);
+            }
+            if (localVarType != null) {
+                out.putShort(cw.newUTF8("LocalVariableTypeTable"));
+                out.putInt(localVarType.length + 2).putShort(localVarTypeCount);
+                out.putByteArray(localVarType.data, 0, localVarType.length);
+            }
+            if (lineNumber != null) {
+                out.putShort(cw.newUTF8("LineNumberTable"));
+                out.putInt(lineNumber.length + 2).putShort(lineNumberCount);
+                out.putByteArray(lineNumber.data, 0, lineNumber.length);
+            }
+            if (stackMap != null) {
+                boolean zip = (cw.version & 0xFFFF) >= Opcodes.V1_6;
+                out.putShort(cw.newUTF8(zip ? "StackMapTable" : "StackMap"));
+                out.putInt(stackMap.length + 2).putShort(frameCount);
+                out.putByteArray(stackMap.data, 0, stackMap.length);
+            }
+            if (cattrs != null) {
+                cattrs.put(cw, code.data, code.length, maxLocals, maxStack, out);
+            }
+        }
+        if (exceptionCount > 0) {
+            out.putShort(cw.newUTF8("Exceptions"))
+                    .putInt(2 * exceptionCount + 2);
+            out.putShort(exceptionCount);
+            for (int i = 0; i < exceptionCount; ++i) {
+                out.putShort(exceptions[i]);
+            }
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0
+                && ((cw.version & 0xFFFF) < Opcodes.V1_5 || (access & ClassWriter.ACC_SYNTHETIC_ATTRIBUTE) != 0))
+        {
+            out.putShort(cw.newUTF8("Synthetic")).putInt(0);
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            out.putShort(cw.newUTF8("Deprecated")).putInt(0);
+        }
+        if (ClassReader.SIGNATURES && signature != null) {
+            out.putShort(cw.newUTF8("Signature"))
+                    .putInt(2)
+                    .putShort(cw.newUTF8(signature));
+        }
+        if (ClassReader.ANNOTATIONS && annd != null) {
+            out.putShort(cw.newUTF8("AnnotationDefault"));
+            out.putInt(annd.length);
+            out.putByteArray(annd.data, 0, annd.length);
+        }
+        if (ClassReader.ANNOTATIONS && anns != null) {
+            out.putShort(cw.newUTF8("RuntimeVisibleAnnotations"));
+            anns.put(out);
+        }
+        if (ClassReader.ANNOTATIONS && ianns != null) {
+            out.putShort(cw.newUTF8("RuntimeInvisibleAnnotations"));
+            ianns.put(out);
+        }
+        if (ClassReader.ANNOTATIONS && panns != null) {
+            out.putShort(cw.newUTF8("RuntimeVisibleParameterAnnotations"));
+            AnnotationWriter.put(panns, synthetics, out);
+        }
+        if (ClassReader.ANNOTATIONS && ipanns != null) {
+            out.putShort(cw.newUTF8("RuntimeInvisibleParameterAnnotations"));
+            AnnotationWriter.put(ipanns, synthetics, out);
+        }
+        if (attrs != null) {
+            attrs.put(cw, null, 0, -1, -1, out);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods: instruction resizing (used to handle GOTO_W and JSR_W)
+    // ------------------------------------------------------------------------
+
+    /**
+     * Resizes and replaces the temporary instructions inserted by
+     * {@link Label#resolve} for wide forward jumps, while keeping jump offsets
+     * and instruction addresses consistent. This may require to resize other
+     * existing instructions, or even to introduce new instructions: for
+     * example, increasing the size of an instruction by 2 at the middle of a
+     * method can increases the offset of an IFEQ instruction from 32766 to
+     * 32768, in which case IFEQ 32766 must be replaced with IFNEQ 8 GOTO_W
+     * 32765. This, in turn, may require to increase the size of another jump
+     * instruction, and so on... All these operations are handled automatically
+     * by this method. <p> <i>This method must be called after all the method
+     * that is being built has been visited</i>. In particular, the
+     * {@link Label Label} objects used to construct the method are no longer
+     * valid after this method has been called.
+     */
+    private void resizeInstructions() {
+        byte[] b = code.data; // bytecode of the method
+        int u, v, label; // indexes in b
+        int i, j; // loop indexes
+        /*
+         * 1st step: As explained above, resizing an instruction may require to
+         * resize another one, which may require to resize yet another one, and
+         * so on. The first step of the algorithm consists in finding all the
+         * instructions that need to be resized, without modifying the code.
+         * This is done by the following "fix point" algorithm:
+         *
+         * Parse the code to find the jump instructions whose offset will need
+         * more than 2 bytes to be stored (the future offset is computed from
+         * the current offset and from the number of bytes that will be inserted
+         * or removed between the source and target instructions). For each such
+         * instruction, adds an entry in (a copy of) the indexes and sizes
+         * arrays (if this has not already been done in a previous iteration!).
+         *
+         * If at least one entry has been added during the previous step, go
+         * back to the beginning, otherwise stop.
+         *
+         * In fact the real algorithm is complicated by the fact that the size
+         * of TABLESWITCH and LOOKUPSWITCH instructions depends on their
+         * position in the bytecode (because of padding). In order to ensure the
+         * convergence of the algorithm, the number of bytes to be added or
+         * removed from these instructions is over estimated during the previous
+         * loop, and computed exactly only after the loop is finished (this
+         * requires another pass to parse the bytecode of the method).
+         */
+        int[] allIndexes = new int[0]; // copy of indexes
+        int[] allSizes = new int[0]; // copy of sizes
+        boolean[] resize; // instructions to be resized
+        int newOffset; // future offset of a jump instruction
+
+        resize = new boolean[code.length];
+
+        // 3 = loop again, 2 = loop ended, 1 = last pass, 0 = done
+        int state = 3;
+        do {
+            if (state == 3) {
+                state = 2;
+            }
+            u = 0;
+            while (u < b.length) {
+                int opcode = b[u] & 0xFF; // opcode of current instruction
+                int insert = 0; // bytes to be added after this instruction
+
+                switch (ClassWriter.TYPE[opcode]) {
+                    case ClassWriter.NOARG_INSN:
+                    case ClassWriter.IMPLVAR_INSN:
+                        u += 1;
+                        break;
+                    case ClassWriter.LABEL_INSN:
+                        if (opcode > 201) {
+                            // converts temporary opcodes 202 to 217, 218 and
+                            // 219 to IFEQ ... JSR (inclusive), IFNULL and
+                            // IFNONNULL
+                            opcode = opcode < 218 ? opcode - 49 : opcode - 20;
+                            label = u + readUnsignedShort(b, u + 1);
+                        } else {
+                            label = u + readShort(b, u + 1);
+                        }
+                        newOffset = getNewOffset(allIndexes, allSizes, u, label);
+                        if (newOffset < Short.MIN_VALUE
+                                || newOffset > Short.MAX_VALUE)
+                        {
+                            if (!resize[u]) {
+                                if (opcode == Opcodes.GOTO
+                                        || opcode == Opcodes.JSR)
+                                {
+                                    // two additional bytes will be required to
+                                    // replace this GOTO or JSR instruction with
+                                    // a GOTO_W or a JSR_W
+                                    insert = 2;
+                                } else {
+                                    // five additional bytes will be required to
+                                    // replace this IFxxx <l> instruction with
+                                    // IFNOTxxx <l'> GOTO_W <l>, where IFNOTxxx
+                                    // is the "opposite" opcode of IFxxx (i.e.,
+                                    // IFNE for IFEQ) and where <l'> designates
+                                    // the instruction just after the GOTO_W.
+                                    insert = 5;
+                                }
+                                resize[u] = true;
+                            }
+                        }
+                        u += 3;
+                        break;
+                    case ClassWriter.LABELW_INSN:
+                        u += 5;
+                        break;
+                    case ClassWriter.TABL_INSN:
+                        if (state == 1) {
+                            // true number of bytes to be added (or removed)
+                            // from this instruction = (future number of padding
+                            // bytes - current number of padding byte) -
+                            // previously over estimated variation =
+                            // = ((3 - newOffset%4) - (3 - u%4)) - u%4
+                            // = (-newOffset%4 + u%4) - u%4
+                            // = -(newOffset & 3)
+                            newOffset = getNewOffset(allIndexes, allSizes, 0, u);
+                            insert = -(newOffset & 3);
+                        } else if (!resize[u]) {
+                            // over estimation of the number of bytes to be
+                            // added to this instruction = 3 - current number
+                            // of padding bytes = 3 - (3 - u%4) = u%4 = u & 3
+                            insert = u & 3;
+                            resize[u] = true;
+                        }
+                        // skips instruction
+                        u = u + 4 - (u & 3);
+                        u += 4 * (readInt(b, u + 8) - readInt(b, u + 4) + 1) + 12;
+                        break;
+                    case ClassWriter.LOOK_INSN:
+                        if (state == 1) {
+                            // like TABL_INSN
+                            newOffset = getNewOffset(allIndexes, allSizes, 0, u);
+                            insert = -(newOffset & 3);
+                        } else if (!resize[u]) {
+                            // like TABL_INSN
+                            insert = u & 3;
+                            resize[u] = true;
+                        }
+                        // skips instruction
+                        u = u + 4 - (u & 3);
+                        u += 8 * readInt(b, u + 4) + 8;
+                        break;
+                    case ClassWriter.WIDE_INSN:
+                        opcode = b[u + 1] & 0xFF;
+                        if (opcode == Opcodes.IINC) {
+                            u += 6;
+                        } else {
+                            u += 4;
+                        }
+                        break;
+                    case ClassWriter.VAR_INSN:
+                    case ClassWriter.SBYTE_INSN:
+                    case ClassWriter.LDC_INSN:
+                        u += 2;
+                        break;
+                    case ClassWriter.SHORT_INSN:
+                    case ClassWriter.LDCW_INSN:
+                    case ClassWriter.FIELDORMETH_INSN:
+                    case ClassWriter.TYPE_INSN:
+                    case ClassWriter.IINC_INSN:
+                        u += 3;
+                        break;
+                    case ClassWriter.ITFMETH_INSN:
+                    case ClassWriter.INDYMETH_INSN:
+                        u += 5;
+                        break;
+                    // case ClassWriter.MANA_INSN:
+                    default:
+                        u += 4;
+                        break;
+                }
+                if (insert != 0) {
+                    // adds a new (u, insert) entry in the allIndexes and
+                    // allSizes arrays
+                    int[] newIndexes = new int[allIndexes.length + 1];
+                    int[] newSizes = new int[allSizes.length + 1];
+                    System.arraycopy(allIndexes,
+                            0,
+                            newIndexes,
+                            0,
+                            allIndexes.length);
+                    System.arraycopy(allSizes, 0, newSizes, 0, allSizes.length);
+                    newIndexes[allIndexes.length] = u;
+                    newSizes[allSizes.length] = insert;
+                    allIndexes = newIndexes;
+                    allSizes = newSizes;
+                    if (insert > 0) {
+                        state = 3;
+                    }
+                }
+            }
+            if (state < 3) {
+                --state;
+            }
+        } while (state != 0);
+
+        // 2nd step:
+        // copies the bytecode of the method into a new bytevector, updates the
+        // offsets, and inserts (or removes) bytes as requested.
+
+        ByteVector newCode = new ByteVector(code.length);
+
+        u = 0;
+        while (u < code.length) {
+            int opcode = b[u] & 0xFF;
+            switch (ClassWriter.TYPE[opcode]) {
+                case ClassWriter.NOARG_INSN:
+                case ClassWriter.IMPLVAR_INSN:
+                    newCode.putByte(opcode);
+                    u += 1;
+                    break;
+                case ClassWriter.LABEL_INSN:
+                    if (opcode > 201) {
+                        // changes temporary opcodes 202 to 217 (inclusive), 218
+                        // and 219 to IFEQ ... JSR (inclusive), IFNULL and
+                        // IFNONNULL
+                        opcode = opcode < 218 ? opcode - 49 : opcode - 20;
+                        label = u + readUnsignedShort(b, u + 1);
+                    } else {
+                        label = u + readShort(b, u + 1);
+                    }
+                    newOffset = getNewOffset(allIndexes, allSizes, u, label);
+                    if (resize[u]) {
+                        // replaces GOTO with GOTO_W, JSR with JSR_W and IFxxx
+                        // <l> with IFNOTxxx <l'> GOTO_W <l>, where IFNOTxxx is
+                        // the "opposite" opcode of IFxxx (i.e., IFNE for IFEQ)
+                        // and where <l'> designates the instruction just after
+                        // the GOTO_W.
+                        if (opcode == Opcodes.GOTO) {
+                            newCode.putByte(200); // GOTO_W
+                        } else if (opcode == Opcodes.JSR) {
+                            newCode.putByte(201); // JSR_W
+                        } else {
+                            newCode.putByte(opcode <= 166
+                                    ? ((opcode + 1) ^ 1) - 1
+                                    : opcode ^ 1);
+                            newCode.putShort(8); // jump offset
+                            newCode.putByte(200); // GOTO_W
+                            // newOffset now computed from start of GOTO_W
+                            newOffset -= 3;
+                        }
+                        newCode.putInt(newOffset);
+                    } else {
+                        newCode.putByte(opcode);
+                        newCode.putShort(newOffset);
+                    }
+                    u += 3;
+                    break;
+                case ClassWriter.LABELW_INSN:
+                    label = u + readInt(b, u + 1);
+                    newOffset = getNewOffset(allIndexes, allSizes, u, label);
+                    newCode.putByte(opcode);
+                    newCode.putInt(newOffset);
+                    u += 5;
+                    break;
+                case ClassWriter.TABL_INSN:
+                    // skips 0 to 3 padding bytes
+                    v = u;
+                    u = u + 4 - (v & 3);
+                    // reads and copies instruction
+                    newCode.putByte(Opcodes.TABLESWITCH);
+                    newCode.putByteArray(null, 0, (4 - newCode.length % 4) % 4);
+                    label = v + readInt(b, u);
+                    u += 4;
+                    newOffset = getNewOffset(allIndexes, allSizes, v, label);
+                    newCode.putInt(newOffset);
+                    j = readInt(b, u);
+                    u += 4;
+                    newCode.putInt(j);
+                    j = readInt(b, u) - j + 1;
+                    u += 4;
+                    newCode.putInt(readInt(b, u - 4));
+                    for (; j > 0; --j) {
+                        label = v + readInt(b, u);
+                        u += 4;
+                        newOffset = getNewOffset(allIndexes, allSizes, v, label);
+                        newCode.putInt(newOffset);
+                    }
+                    break;
+                case ClassWriter.LOOK_INSN:
+                    // skips 0 to 3 padding bytes
+                    v = u;
+                    u = u + 4 - (v & 3);
+                    // reads and copies instruction
+                    newCode.putByte(Opcodes.LOOKUPSWITCH);
+                    newCode.putByteArray(null, 0, (4 - newCode.length % 4) % 4);
+                    label = v + readInt(b, u);
+                    u += 4;
+                    newOffset = getNewOffset(allIndexes, allSizes, v, label);
+                    newCode.putInt(newOffset);
+                    j = readInt(b, u);
+                    u += 4;
+                    newCode.putInt(j);
+                    for (; j > 0; --j) {
+                        newCode.putInt(readInt(b, u));
+                        u += 4;
+                        label = v + readInt(b, u);
+                        u += 4;
+                        newOffset = getNewOffset(allIndexes, allSizes, v, label);
+                        newCode.putInt(newOffset);
+                    }
+                    break;
+                case ClassWriter.WIDE_INSN:
+                    opcode = b[u + 1] & 0xFF;
+                    if (opcode == Opcodes.IINC) {
+                        newCode.putByteArray(b, u, 6);
+                        u += 6;
+                    } else {
+                        newCode.putByteArray(b, u, 4);
+                        u += 4;
+                    }
+                    break;
+                case ClassWriter.VAR_INSN:
+                case ClassWriter.SBYTE_INSN:
+                case ClassWriter.LDC_INSN:
+                    newCode.putByteArray(b, u, 2);
+                    u += 2;
+                    break;
+                case ClassWriter.SHORT_INSN:
+                case ClassWriter.LDCW_INSN:
+                case ClassWriter.FIELDORMETH_INSN:
+                case ClassWriter.TYPE_INSN:
+                case ClassWriter.IINC_INSN:
+                    newCode.putByteArray(b, u, 3);
+                    u += 3;
+                    break;
+                case ClassWriter.ITFMETH_INSN:
+                case ClassWriter.INDYMETH_INSN:
+                    newCode.putByteArray(b, u, 5);
+                    u += 5;
+                    break;
+                // case MANA_INSN:
+                default:
+                    newCode.putByteArray(b, u, 4);
+                    u += 4;
+                    break;
+            }
+        }
+
+        // recomputes the stack map frames
+        if (frameCount > 0) {
+            if (compute == FRAMES) {
+                frameCount = 0;
+                stackMap = null;
+                previousFrame = null;
+                frame = null;
+                Frame f = new Frame();
+                f.owner = labels;
+                Type[] args = Type.getArgumentTypes(descriptor);
+                f.initInputFrame(cw, access, args, maxLocals);
+                visitFrame(f);
+                Label l = labels;
+                while (l != null) {
+                    /*
+                     * here we need the original label position. getNewOffset
+                     * must therefore never have been called for this label.
+                     */
+                    u = l.position - 3;
+                    if ((l.status & Label.STORE) != 0 || (u >= 0 && resize[u]))
+                    {
+                        getNewOffset(allIndexes, allSizes, l);
+                        // TODO update offsets in UNINITIALIZED values
+                        visitFrame(l.frame);
+                    }
+                    l = l.successor;
+                }
+            } else {
+                /*
+                 * Resizing an existing stack map frame table is really hard.
+                 * Not only the table must be parsed to update the offets, but
+                 * new frames may be needed for jump instructions that were
+                 * inserted by this method. And updating the offsets or
+                 * inserting frames can change the format of the following
+                 * frames, in case of packed frames. In practice the whole table
+                 * must be recomputed. For this the frames are marked as
+                 * potentially invalid. This will cause the whole class to be
+                 * reread and rewritten with the COMPUTE_FRAMES option (see the
+                 * ClassWriter.toByteArray method). This is not very efficient
+                 * but is much easier and requires much less code than any other
+                 * method I can think of.
+                 */
+                cw.invalidFrames = true;
+            }
+        }
+        // updates the exception handler block labels
+        Handler h = firstHandler;
+        while (h != null) {
+            getNewOffset(allIndexes, allSizes, h.start);
+            getNewOffset(allIndexes, allSizes, h.end);
+            getNewOffset(allIndexes, allSizes, h.handler);
+            h = h.next;
+        }
+        // updates the instructions addresses in the
+        // local var and line number tables
+        for (i = 0; i < 2; ++i) {
+            ByteVector bv = i == 0 ? localVar : localVarType;
+            if (bv != null) {
+                b = bv.data;
+                u = 0;
+                while (u < bv.length) {
+                    label = readUnsignedShort(b, u);
+                    newOffset = getNewOffset(allIndexes, allSizes, 0, label);
+                    writeShort(b, u, newOffset);
+                    label += readUnsignedShort(b, u + 2);
+                    newOffset = getNewOffset(allIndexes, allSizes, 0, label)
+                            - newOffset;
+                    writeShort(b, u + 2, newOffset);
+                    u += 10;
+                }
+            }
+        }
+        if (lineNumber != null) {
+            b = lineNumber.data;
+            u = 0;
+            while (u < lineNumber.length) {
+                writeShort(b, u, getNewOffset(allIndexes,
+                        allSizes,
+                        0,
+                        readUnsignedShort(b, u)));
+                u += 4;
+            }
+        }
+        // updates the labels of the other attributes
+        Attribute attr = cattrs;
+        while (attr != null) {
+            Label[] labels = attr.getLabels();
+            if (labels != null) {
+                for (i = labels.length - 1; i >= 0; --i) {
+                    getNewOffset(allIndexes, allSizes, labels[i]);
+                }
+            }
+            attr = attr.next;
+        }
+
+        // replaces old bytecodes with new ones
+        code = newCode;
+    }
+
+    /**
+     * Reads an unsigned short value in the given byte array.
+     *
+     * @param b a byte array.
+     * @param index the start index of the value to be read.
+     * @return the read value.
+     */
+    static int readUnsignedShort(final byte[] b, final int index) {
+        return ((b[index] & 0xFF) << 8) | (b[index + 1] & 0xFF);
+    }
+
+    /**
+     * Reads a signed short value in the given byte array.
+     *
+     * @param b a byte array.
+     * @param index the start index of the value to be read.
+     * @return the read value.
+     */
+    static short readShort(final byte[] b, final int index) {
+        return (short) (((b[index] & 0xFF) << 8) | (b[index + 1] & 0xFF));
+    }
+
+    /**
+     * Reads a signed int value in the given byte array.
+     *
+     * @param b a byte array.
+     * @param index the start index of the value to be read.
+     * @return the read value.
+     */
+    static int readInt(final byte[] b, final int index) {
+        return ((b[index] & 0xFF) << 24) | ((b[index + 1] & 0xFF) << 16)
+                | ((b[index + 2] & 0xFF) << 8) | (b[index + 3] & 0xFF);
+    }
+
+    /**
+     * Writes a short value in the given byte array.
+     *
+     * @param b a byte array.
+     * @param index where the first byte of the short value must be written.
+     * @param s the value to be written in the given byte array.
+     */
+    static void writeShort(final byte[] b, final int index, final int s) {
+        b[index] = (byte) (s >>> 8);
+        b[index + 1] = (byte) s;
+    }
+
+    /**
+     * Computes the future value of a bytecode offset. <p> Note: it is possible
+     * to have several entries for the same instruction in the <tt>indexes</tt>
+     * and <tt>sizes</tt>: two entries (index=a,size=b) and (index=a,size=b')
+     * are equivalent to a single entry (index=a,size=b+b').
+     *
+     * @param indexes current positions of the instructions to be resized. Each
+     *        instruction must be designated by the index of its <i>last</i>
+     *        byte, plus one (or, in other words, by the index of the <i>first</i>
+     *        byte of the <i>next</i> instruction).
+     * @param sizes the number of bytes to be <i>added</i> to the above
+     *        instructions. More precisely, for each i < <tt>len</tt>,
+     *        <tt>sizes</tt>[i] bytes will be added at the end of the
+     *        instruction designated by <tt>indexes</tt>[i] or, if
+     *        <tt>sizes</tt>[i] is negative, the <i>last</i> |<tt>sizes[i]</tt>|
+     *        bytes of the instruction will be removed (the instruction size
+     *        <i>must not</i> become negative or null).
+     * @param begin index of the first byte of the source instruction.
+     * @param end index of the first byte of the target instruction.
+     * @return the future value of the given bytecode offset.
+     */
+    static int getNewOffset(
+        final int[] indexes,
+        final int[] sizes,
+        final int begin,
+        final int end)
+    {
+        int offset = end - begin;
+        for (int i = 0; i < indexes.length; ++i) {
+            if (begin < indexes[i] && indexes[i] <= end) {
+                // forward jump
+                offset += sizes[i];
+            } else if (end < indexes[i] && indexes[i] <= begin) {
+                // backward jump
+                offset -= sizes[i];
+            }
+        }
+        return offset;
+    }
+
+    /**
+     * Updates the offset of the given label.
+     *
+     * @param indexes current positions of the instructions to be resized. Each
+     *        instruction must be designated by the index of its <i>last</i>
+     *        byte, plus one (or, in other words, by the index of the <i>first</i>
+     *        byte of the <i>next</i> instruction).
+     * @param sizes the number of bytes to be <i>added</i> to the above
+     *        instructions. More precisely, for each i < <tt>len</tt>,
+     *        <tt>sizes</tt>[i] bytes will be added at the end of the
+     *        instruction designated by <tt>indexes</tt>[i] or, if
+     *        <tt>sizes</tt>[i] is negative, the <i>last</i> |<tt>sizes[i]</tt>|
+     *        bytes of the instruction will be removed (the instruction size
+     *        <i>must not</i> become negative or null).
+     * @param label the label whose offset must be updated.
+     */
+    static void getNewOffset(
+        final int[] indexes,
+        final int[] sizes,
+        final Label label)
+    {
+        if ((label.status & Label.RESIZED) == 0) {
+            label.position = getNewOffset(indexes, sizes, 0, label.position);
+            label.status |= Label.RESIZED;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Opcodes.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,387 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+/**
+ * Defines the JVM opcodes, access flags and array type codes. This interface
+ * does not define all the JVM opcodes because some opcodes are automatically
+ * handled. For example, the xLOAD and xSTORE opcodes are automatically replaced
+ * by xLOAD_n and xSTORE_n opcodes when possible. The xLOAD_n and xSTORE_n
+ * opcodes are therefore not defined in this interface. Likewise for LDC,
+ * automatically replaced by LDC_W or LDC2_W when necessary, WIDE, GOTO_W and
+ * JSR_W.
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+public interface Opcodes {
+
+    // ASM API versions
+
+    int ASM4 = 4 << 16 | 0 << 8 | 0;
+
+    // versions
+
+    int V1_1 = 3 << 16 | 45;
+    int V1_2 = 0 << 16 | 46;
+    int V1_3 = 0 << 16 | 47;
+    int V1_4 = 0 << 16 | 48;
+    int V1_5 = 0 << 16 | 49;
+    int V1_6 = 0 << 16 | 50;
+    int V1_7 = 0 << 16 | 51;
+
+    // access flags
+
+    int ACC_PUBLIC = 0x0001; // class, field, method
+    int ACC_PRIVATE = 0x0002; // class, field, method
+    int ACC_PROTECTED = 0x0004; // class, field, method
+    int ACC_STATIC = 0x0008; // field, method
+    int ACC_FINAL = 0x0010; // class, field, method
+    int ACC_SUPER = 0x0020; // class
+    int ACC_SYNCHRONIZED = 0x0020; // method
+    int ACC_VOLATILE = 0x0040; // field
+    int ACC_BRIDGE = 0x0040; // method
+    int ACC_VARARGS = 0x0080; // method
+    int ACC_TRANSIENT = 0x0080; // field
+    int ACC_NATIVE = 0x0100; // method
+    int ACC_INTERFACE = 0x0200; // class
+    int ACC_ABSTRACT = 0x0400; // class, method
+    int ACC_STRICT = 0x0800; // method
+    int ACC_SYNTHETIC = 0x1000; // class, field, method
+    int ACC_ANNOTATION = 0x2000; // class
+    int ACC_ENUM = 0x4000; // class(?) field inner
+
+    // ASM specific pseudo access flags
+
+    int ACC_DEPRECATED = 0x20000; // class, field, method
+
+    // types for NEWARRAY
+
+    int T_BOOLEAN = 4;
+    int T_CHAR = 5;
+    int T_FLOAT = 6;
+    int T_DOUBLE = 7;
+    int T_BYTE = 8;
+    int T_SHORT = 9;
+    int T_INT = 10;
+    int T_LONG = 11;
+
+    // tags for Handle
+
+    int H_GETFIELD = 1;
+    int H_GETSTATIC = 2;
+    int H_PUTFIELD = 3;
+    int H_PUTSTATIC = 4;
+    int H_INVOKEVIRTUAL = 5;
+    int H_INVOKESTATIC = 6;
+    int H_INVOKESPECIAL = 7;
+    int H_NEWINVOKESPECIAL = 8;
+    int H_INVOKEINTERFACE = 9;
+
+    // stack map frame types
+
+    /**
+     * Represents an expanded frame. See {@link ClassReader#EXPAND_FRAMES}.
+     */
+    int F_NEW = -1;
+
+    /**
+     * Represents a compressed frame with complete frame data.
+     */
+    int F_FULL = 0;
+
+    /**
+     * Represents a compressed frame where locals are the same as the locals in
+     * the previous frame, except that additional 1-3 locals are defined, and
+     * with an empty stack.
+     */
+    int F_APPEND = 1;
+
+    /**
+     * Represents a compressed frame where locals are the same as the locals in
+     * the previous frame, except that the last 1-3 locals are absent and with
+     * an empty stack.
+     */
+    int F_CHOP = 2;
+
+    /**
+     * Represents a compressed frame with exactly the same locals as the
+     * previous frame and with an empty stack.
+     */
+    int F_SAME = 3;
+
+    /**
+     * Represents a compressed frame with exactly the same locals as the
+     * previous frame and with a single value on the stack.
+     */
+    int F_SAME1 = 4;
+
+    Integer TOP = new Integer(0);
+    Integer INTEGER = new Integer(1);
+    Integer FLOAT = new Integer(2);
+    Integer DOUBLE = new Integer(3);
+    Integer LONG = new Integer(4);
+    Integer NULL = new Integer(5);
+    Integer UNINITIALIZED_THIS = new Integer(6);
+
+    // opcodes // visit method (- = idem)
+
+    int NOP = 0; // visitInsn
+    int ACONST_NULL = 1; // -
+    int ICONST_M1 = 2; // -
+    int ICONST_0 = 3; // -
+    int ICONST_1 = 4; // -
+    int ICONST_2 = 5; // -
+    int ICONST_3 = 6; // -
+    int ICONST_4 = 7; // -
+    int ICONST_5 = 8; // -
+    int LCONST_0 = 9; // -
+    int LCONST_1 = 10; // -
+    int FCONST_0 = 11; // -
+    int FCONST_1 = 12; // -
+    int FCONST_2 = 13; // -
+    int DCONST_0 = 14; // -
+    int DCONST_1 = 15; // -
+    int BIPUSH = 16; // visitIntInsn
+    int SIPUSH = 17; // -
+    int LDC = 18; // visitLdcInsn
+    // int LDC_W = 19; // -
+    // int LDC2_W = 20; // -
+    int ILOAD = 21; // visitVarInsn
+    int LLOAD = 22; // -
+    int FLOAD = 23; // -
+    int DLOAD = 24; // -
+    int ALOAD = 25; // -
+    // int ILOAD_0 = 26; // -
+    // int ILOAD_1 = 27; // -
+    // int ILOAD_2 = 28; // -
+    // int ILOAD_3 = 29; // -
+    // int LLOAD_0 = 30; // -
+    // int LLOAD_1 = 31; // -
+    // int LLOAD_2 = 32; // -
+    // int LLOAD_3 = 33; // -
+    // int FLOAD_0 = 34; // -
+    // int FLOAD_1 = 35; // -
+    // int FLOAD_2 = 36; // -
+    // int FLOAD_3 = 37; // -
+    // int DLOAD_0 = 38; // -
+    // int DLOAD_1 = 39; // -
+    // int DLOAD_2 = 40; // -
+    // int DLOAD_3 = 41; // -
+    // int ALOAD_0 = 42; // -
+    // int ALOAD_1 = 43; // -
+    // int ALOAD_2 = 44; // -
+    // int ALOAD_3 = 45; // -
+    int IALOAD = 46; // visitInsn
+    int LALOAD = 47; // -
+    int FALOAD = 48; // -
+    int DALOAD = 49; // -
+    int AALOAD = 50; // -
+    int BALOAD = 51; // -
+    int CALOAD = 52; // -
+    int SALOAD = 53; // -
+    int ISTORE = 54; // visitVarInsn
+    int LSTORE = 55; // -
+    int FSTORE = 56; // -
+    int DSTORE = 57; // -
+    int ASTORE = 58; // -
+    // int ISTORE_0 = 59; // -
+    // int ISTORE_1 = 60; // -
+    // int ISTORE_2 = 61; // -
+    // int ISTORE_3 = 62; // -
+    // int LSTORE_0 = 63; // -
+    // int LSTORE_1 = 64; // -
+    // int LSTORE_2 = 65; // -
+    // int LSTORE_3 = 66; // -
+    // int FSTORE_0 = 67; // -
+    // int FSTORE_1 = 68; // -
+    // int FSTORE_2 = 69; // -
+    // int FSTORE_3 = 70; // -
+    // int DSTORE_0 = 71; // -
+    // int DSTORE_1 = 72; // -
+    // int DSTORE_2 = 73; // -
+    // int DSTORE_3 = 74; // -
+    // int ASTORE_0 = 75; // -
+    // int ASTORE_1 = 76; // -
+    // int ASTORE_2 = 77; // -
+    // int ASTORE_3 = 78; // -
+    int IASTORE = 79; // visitInsn
+    int LASTORE = 80; // -
+    int FASTORE = 81; // -
+    int DASTORE = 82; // -
+    int AASTORE = 83; // -
+    int BASTORE = 84; // -
+    int CASTORE = 85; // -
+    int SASTORE = 86; // -
+    int POP = 87; // -
+    int POP2 = 88; // -
+    int DUP = 89; // -
+    int DUP_X1 = 90; // -
+    int DUP_X2 = 91; // -
+    int DUP2 = 92; // -
+    int DUP2_X1 = 93; // -
+    int DUP2_X2 = 94; // -
+    int SWAP = 95; // -
+    int IADD = 96; // -
+    int LADD = 97; // -
+    int FADD = 98; // -
+    int DADD = 99; // -
+    int ISUB = 100; // -
+    int LSUB = 101; // -
+    int FSUB = 102; // -
+    int DSUB = 103; // -
+    int IMUL = 104; // -
+    int LMUL = 105; // -
+    int FMUL = 106; // -
+    int DMUL = 107; // -
+    int IDIV = 108; // -
+    int LDIV = 109; // -
+    int FDIV = 110; // -
+    int DDIV = 111; // -
+    int IREM = 112; // -
+    int LREM = 113; // -
+    int FREM = 114; // -
+    int DREM = 115; // -
+    int INEG = 116; // -
+    int LNEG = 117; // -
+    int FNEG = 118; // -
+    int DNEG = 119; // -
+    int ISHL = 120; // -
+    int LSHL = 121; // -
+    int ISHR = 122; // -
+    int LSHR = 123; // -
+    int IUSHR = 124; // -
+    int LUSHR = 125; // -
+    int IAND = 126; // -
+    int LAND = 127; // -
+    int IOR = 128; // -
+    int LOR = 129; // -
+    int IXOR = 130; // -
+    int LXOR = 131; // -
+    int IINC = 132; // visitIincInsn
+    int I2L = 133; // visitInsn
+    int I2F = 134; // -
+    int I2D = 135; // -
+    int L2I = 136; // -
+    int L2F = 137; // -
+    int L2D = 138; // -
+    int F2I = 139; // -
+    int F2L = 140; // -
+    int F2D = 141; // -
+    int D2I = 142; // -
+    int D2L = 143; // -
+    int D2F = 144; // -
+    int I2B = 145; // -
+    int I2C = 146; // -
+    int I2S = 147; // -
+    int LCMP = 148; // -
+    int FCMPL = 149; // -
+    int FCMPG = 150; // -
+    int DCMPL = 151; // -
+    int DCMPG = 152; // -
+    int IFEQ = 153; // visitJumpInsn
+    int IFNE = 154; // -
+    int IFLT = 155; // -
+    int IFGE = 156; // -
+    int IFGT = 157; // -
+    int IFLE = 158; // -
+    int IF_ICMPEQ = 159; // -
+    int IF_ICMPNE = 160; // -
+    int IF_ICMPLT = 161; // -
+    int IF_ICMPGE = 162; // -
+    int IF_ICMPGT = 163; // -
+    int IF_ICMPLE = 164; // -
+    int IF_ACMPEQ = 165; // -
+    int IF_ACMPNE = 166; // -
+    int GOTO = 167; // -
+    int JSR = 168; // -
+    int RET = 169; // visitVarInsn
+    int TABLESWITCH = 170; // visiTableSwitchInsn
+    int LOOKUPSWITCH = 171; // visitLookupSwitch
+    int IRETURN = 172; // visitInsn
+    int LRETURN = 173; // -
+    int FRETURN = 174; // -
+    int DRETURN = 175; // -
+    int ARETURN = 176; // -
+    int RETURN = 177; // -
+    int GETSTATIC = 178; // visitFieldInsn
+    int PUTSTATIC = 179; // -
+    int GETFIELD = 180; // -
+    int PUTFIELD = 181; // -
+    int INVOKEVIRTUAL = 182; // visitMethodInsn
+    int INVOKESPECIAL = 183; // -
+    int INVOKESTATIC = 184; // -
+    int INVOKEINTERFACE = 185; // -
+    int INVOKEDYNAMIC = 186; // visitInvokeDynamicInsn
+    int NEW = 187; // visitTypeInsn
+    int NEWARRAY = 188; // visitIntInsn
+    int ANEWARRAY = 189; // visitTypeInsn
+    int ARRAYLENGTH = 190; // visitInsn
+    int ATHROW = 191; // -
+    int CHECKCAST = 192; // visitTypeInsn
+    int INSTANCEOF = 193; // -
+    int MONITORENTER = 194; // visitInsn
+    int MONITOREXIT = 195; // -
+    // int WIDE = 196; // NOT VISITED
+    int MULTIANEWARRAY = 197; // visitMultiANewArrayInsn
+    int IFNULL = 198; // visitJumpInsn
+    int IFNONNULL = 199; // -
+    // int GOTO_W = 200; // -
+    // int JSR_W = 201; // -
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/Type.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,894 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm;
+
+import java.lang.reflect.Constructor;
+import java.lang.reflect.Method;
+
+/**
+ * A Java field or method type. This class can be used to make it easier to
+ * manipulate type and method descriptors.
+ *
+ * @author Eric Bruneton
+ * @author Chris Nokleberg
+ */
+public class Type {
+
+    /**
+     * The sort of the <tt>void</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int VOID = 0;
+
+    /**
+     * The sort of the <tt>boolean</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int BOOLEAN = 1;
+
+    /**
+     * The sort of the <tt>char</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int CHAR = 2;
+
+    /**
+     * The sort of the <tt>byte</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int BYTE = 3;
+
+    /**
+     * The sort of the <tt>short</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int SHORT = 4;
+
+    /**
+     * The sort of the <tt>int</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int INT = 5;
+
+    /**
+     * The sort of the <tt>float</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int FLOAT = 6;
+
+    /**
+     * The sort of the <tt>long</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int LONG = 7;
+
+    /**
+     * The sort of the <tt>double</tt> type. See {@link #getSort getSort}.
+     */
+    public static final int DOUBLE = 8;
+
+    /**
+     * The sort of array reference types. See {@link #getSort getSort}.
+     */
+    public static final int ARRAY = 9;
+
+    /**
+     * The sort of object reference types. See {@link #getSort getSort}.
+     */
+    public static final int OBJECT = 10;
+
+    /**
+     * The sort of method types. See {@link #getSort getSort}.
+     */
+    public static final int METHOD = 11;
+
+    /**
+     * The <tt>void</tt> type.
+     */
+    public static final Type VOID_TYPE = new Type(VOID, null, ('V' << 24)
+            | (5 << 16) | (0 << 8) | 0, 1);
+
+    /**
+     * The <tt>boolean</tt> type.
+     */
+    public static final Type BOOLEAN_TYPE = new Type(BOOLEAN, null, ('Z' << 24)
+            | (0 << 16) | (5 << 8) | 1, 1);
+
+    /**
+     * The <tt>char</tt> type.
+     */
+    public static final Type CHAR_TYPE = new Type(CHAR, null, ('C' << 24)
+            | (0 << 16) | (6 << 8) | 1, 1);
+
+    /**
+     * The <tt>byte</tt> type.
+     */
+    public static final Type BYTE_TYPE = new Type(BYTE, null, ('B' << 24)
+            | (0 << 16) | (5 << 8) | 1, 1);
+
+    /**
+     * The <tt>short</tt> type.
+     */
+    public static final Type SHORT_TYPE = new Type(SHORT, null, ('S' << 24)
+            | (0 << 16) | (7 << 8) | 1, 1);
+
+    /**
+     * The <tt>int</tt> type.
+     */
+    public static final Type INT_TYPE = new Type(INT, null, ('I' << 24)
+            | (0 << 16) | (0 << 8) | 1, 1);
+
+    /**
+     * The <tt>float</tt> type.
+     */
+    public static final Type FLOAT_TYPE = new Type(FLOAT, null, ('F' << 24)
+            | (2 << 16) | (2 << 8) | 1, 1);
+
+    /**
+     * The <tt>long</tt> type.
+     */
+    public static final Type LONG_TYPE = new Type(LONG, null, ('J' << 24)
+            | (1 << 16) | (1 << 8) | 2, 1);
+
+    /**
+     * The <tt>double</tt> type.
+     */
+    public static final Type DOUBLE_TYPE = new Type(DOUBLE, null, ('D' << 24)
+            | (3 << 16) | (3 << 8) | 2, 1);
+
+    // ------------------------------------------------------------------------
+    // Fields
+    // ------------------------------------------------------------------------
+
+    /**
+     * The sort of this Java type.
+     */
+    private final int sort;
+
+    /**
+     * A buffer containing the internal name of this Java type. This field is
+     * only used for reference types.
+     */
+    private final char[] buf;
+
+    /**
+     * The offset of the internal name of this Java type in {@link #buf buf} or,
+     * for primitive types, the size, descriptor and getOpcode offsets for this
+     * type (byte 0 contains the size, byte 1 the descriptor, byte 2 the offset
+     * for IALOAD or IASTORE, byte 3 the offset for all other instructions).
+     */
+    private final int off;
+
+    /**
+     * The length of the internal name of this Java type.
+     */
+    private final int len;
+
+    // ------------------------------------------------------------------------
+    // Constructors
+    // ------------------------------------------------------------------------
+
+    /**
+     * Constructs a reference type.
+     *
+     * @param sort the sort of the reference type to be constructed.
+     * @param buf a buffer containing the descriptor of the previous type.
+     * @param off the offset of this descriptor in the previous buffer.
+     * @param len the length of this descriptor.
+     */
+    private Type(final int sort, final char[] buf, final int off, final int len)
+    {
+        this.sort = sort;
+        this.buf = buf;
+        this.off = off;
+        this.len = len;
+    }
+
+    /**
+     * Returns the Java type corresponding to the given type descriptor.
+     *
+     * @param typeDescriptor a field or method type descriptor.
+     * @return the Java type corresponding to the given type descriptor.
+     */
+    public static Type getType(final String typeDescriptor) {
+        return getType(typeDescriptor.toCharArray(), 0);
+    }
+
+    /**
+     * Returns the Java type corresponding to the given internal name.
+     *
+     * @param internalName an internal name.
+     * @return the Java type corresponding to the given internal name.
+     */
+    public static Type getObjectType(final String internalName) {
+        char[] buf = internalName.toCharArray();
+        return new Type(buf[0] == '[' ? ARRAY : OBJECT, buf, 0, buf.length);
+    }
+
+    /**
+     * Returns the Java type corresponding to the given method descriptor.
+     * Equivalent to <code>Type.getType(methodDescriptor)</code>.
+     *
+     * @param methodDescriptor a method descriptor.
+     * @return the Java type corresponding to the given method descriptor.
+     */
+    public static Type getMethodType(final String methodDescriptor) {
+        return getType(methodDescriptor.toCharArray(), 0);
+    }
+
+    /**
+     * Returns the Java method type corresponding to the given argument and
+     * return types.
+     *
+     * @param returnType the return type of the method.
+     * @param argumentTypes the argument types of the method.
+     * @return the Java type corresponding to the given argument and return types.
+     */
+    public static Type getMethodType(final Type returnType, final Type... argumentTypes) {
+        return getType(getMethodDescriptor(returnType, argumentTypes));
+    }
+
+    /**
+     * Returns the Java type corresponding to the given class.
+     *
+     * @param c a class.
+     * @return the Java type corresponding to the given class.
+     */
+    public static Type getType(final Class<?> c) {
+        if (c.isPrimitive()) {
+            if (c == Integer.TYPE) {
+                return INT_TYPE;
+            } else if (c == Void.TYPE) {
+                return VOID_TYPE;
+            } else if (c == Boolean.TYPE) {
+                return BOOLEAN_TYPE;
+            } else if (c == Byte.TYPE) {
+                return BYTE_TYPE;
+            } else if (c == Character.TYPE) {
+                return CHAR_TYPE;
+            } else if (c == Short.TYPE) {
+                return SHORT_TYPE;
+            } else if (c == Double.TYPE) {
+                return DOUBLE_TYPE;
+            } else if (c == Float.TYPE) {
+                return FLOAT_TYPE;
+            } else /* if (c == Long.TYPE) */{
+                return LONG_TYPE;
+            }
+        } else {
+            return getType(getDescriptor(c));
+        }
+    }
+
+    /**
+     * Returns the Java method type corresponding to the given constructor.
+     *
+     * @param c a {@link Constructor Constructor} object.
+     * @return the Java method type corresponding to the given constructor.
+     */
+    public static Type getType(final Constructor<?> c) {
+        return getType(getConstructorDescriptor(c));
+    }
+
+    /**
+     * Returns the Java method type corresponding to the given method.
+     *
+     * @param m a {@link Method Method} object.
+     * @return the Java method type corresponding to the given method.
+     */
+    public static Type getType(final Method m) {
+        return getType(getMethodDescriptor(m));
+    }
+
+    /**
+     * Returns the Java types corresponding to the argument types of the given
+     * method descriptor.
+     *
+     * @param methodDescriptor a method descriptor.
+     * @return the Java types corresponding to the argument types of the given
+     *         method descriptor.
+     */
+    public static Type[] getArgumentTypes(final String methodDescriptor) {
+        char[] buf = methodDescriptor.toCharArray();
+        int off = 1;
+        int size = 0;
+        while (true) {
+            char car = buf[off++];
+            if (car == ')') {
+                break;
+            } else if (car == 'L') {
+                while (buf[off++] != ';') {
+                }
+                ++size;
+            } else if (car != '[') {
+                ++size;
+            }
+        }
+        Type[] args = new Type[size];
+        off = 1;
+        size = 0;
+        while (buf[off] != ')') {
+            args[size] = getType(buf, off);
+            off += args[size].len + (args[size].sort == OBJECT ? 2 : 0);
+            size += 1;
+        }
+        return args;
+    }
+
+    /**
+     * Returns the Java types corresponding to the argument types of the given
+     * method.
+     *
+     * @param method a method.
+     * @return the Java types corresponding to the argument types of the given
+     *         method.
+     */
+    public static Type[] getArgumentTypes(final Method method) {
+        Class<?>[] classes = method.getParameterTypes();
+        Type[] types = new Type[classes.length];
+        for (int i = classes.length - 1; i >= 0; --i) {
+            types[i] = getType(classes[i]);
+        }
+        return types;
+    }
+
+    /**
+     * Returns the Java type corresponding to the return type of the given
+     * method descriptor.
+     *
+     * @param methodDescriptor a method descriptor.
+     * @return the Java type corresponding to the return type of the given
+     *         method descriptor.
+     */
+    public static Type getReturnType(final String methodDescriptor) {
+        char[] buf = methodDescriptor.toCharArray();
+        return getType(buf, methodDescriptor.indexOf(')') + 1);
+    }
+
+    /**
+     * Returns the Java type corresponding to the return type of the given
+     * method.
+     *
+     * @param method a method.
+     * @return the Java type corresponding to the return type of the given
+     *         method.
+     */
+    public static Type getReturnType(final Method method) {
+        return getType(method.getReturnType());
+    }
+
+    /**
+     * Computes the size of the arguments and of the return value of a method.
+     *
+     * @param desc the descriptor of a method.
+     * @return the size of the arguments of the method (plus one for the
+     *         implicit this argument), argSize, and the size of its return
+     *         value, retSize, packed into a single int i =
+     *         <tt>(argSize << 2) | retSize</tt> (argSize is therefore equal
+     *         to <tt>i >> 2</tt>, and retSize to <tt>i & 0x03</tt>).
+     */
+    public static int getArgumentsAndReturnSizes(final String desc) {
+        int n = 1;
+        int c = 1;
+        while (true) {
+            char car = desc.charAt(c++);
+            if (car == ')') {
+                car = desc.charAt(c);
+                return n << 2
+                        | (car == 'V' ? 0 : (car == 'D' || car == 'J' ? 2 : 1));
+            } else if (car == 'L') {
+                while (desc.charAt(c++) != ';') {
+                }
+                n += 1;
+            } else if (car == '[') {
+                while ((car = desc.charAt(c)) == '[') {
+                    ++c;
+                }
+                if (car == 'D' || car == 'J') {
+                    n -= 1;
+                }
+            } else if (car == 'D' || car == 'J') {
+                n += 2;
+            } else {
+                n += 1;
+            }
+        }
+    }
+
+    /**
+     * Returns the Java type corresponding to the given type descriptor. For
+     * method descriptors, buf is supposed to contain nothing more than the
+     * descriptor itself.
+     *
+     * @param buf a buffer containing a type descriptor.
+     * @param off the offset of this descriptor in the previous buffer.
+     * @return the Java type corresponding to the given type descriptor.
+     */
+    private static Type getType(final char[] buf, final int off) {
+        int len;
+        switch (buf[off]) {
+            case 'V':
+                return VOID_TYPE;
+            case 'Z':
+                return BOOLEAN_TYPE;
+            case 'C':
+                return CHAR_TYPE;
+            case 'B':
+                return BYTE_TYPE;
+            case 'S':
+                return SHORT_TYPE;
+            case 'I':
+                return INT_TYPE;
+            case 'F':
+                return FLOAT_TYPE;
+            case 'J':
+                return LONG_TYPE;
+            case 'D':
+                return DOUBLE_TYPE;
+            case '[':
+                len = 1;
+                while (buf[off + len] == '[') {
+                    ++len;
+                }
+                if (buf[off + len] == 'L') {
+                    ++len;
+                    while (buf[off + len] != ';') {
+                        ++len;
+                    }
+                }
+                return new Type(ARRAY, buf, off, len + 1);
+            case 'L':
+                len = 1;
+                while (buf[off + len] != ';') {
+                    ++len;
+                }
+                return new Type(OBJECT, buf, off + 1, len - 1);
+            // case '(':
+            default:
+                return new Type(METHOD, buf, 0, buf.length);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Accessors
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the sort of this Java type.
+     *
+     * @return {@link #VOID VOID}, {@link #BOOLEAN BOOLEAN},
+     *         {@link #CHAR CHAR}, {@link #BYTE BYTE}, {@link #SHORT SHORT},
+     *         {@link #INT INT}, {@link #FLOAT FLOAT}, {@link #LONG LONG},
+     *         {@link #DOUBLE DOUBLE}, {@link #ARRAY ARRAY},
+     *         {@link #OBJECT OBJECT} or {@link #METHOD METHOD}.
+     */
+    public int getSort() {
+        return sort;
+    }
+
+    /**
+     * Returns the number of dimensions of this array type. This method should
+     * only be used for an array type.
+     *
+     * @return the number of dimensions of this array type.
+     */
+    public int getDimensions() {
+        int i = 1;
+        while (buf[off + i] == '[') {
+            ++i;
+        }
+        return i;
+    }
+
+    /**
+     * Returns the type of the elements of this array type. This method should
+     * only be used for an array type.
+     *
+     * @return Returns the type of the elements of this array type.
+     */
+    public Type getElementType() {
+        return getType(buf, off + getDimensions());
+    }
+
+    /**
+     * Returns the binary name of the class corresponding to this type. This
+     * method must not be used on method types.
+     *
+     * @return the binary name of the class corresponding to this type.
+     */
+    public String getClassName() {
+        switch (sort) {
+            case VOID:
+                return "void";
+            case BOOLEAN:
+                return "boolean";
+            case CHAR:
+                return "char";
+            case BYTE:
+                return "byte";
+            case SHORT:
+                return "short";
+            case INT:
+                return "int";
+            case FLOAT:
+                return "float";
+            case LONG:
+                return "long";
+            case DOUBLE:
+                return "double";
+            case ARRAY:
+                StringBuffer b = new StringBuffer(getElementType().getClassName());
+                for (int i = getDimensions(); i > 0; --i) {
+                    b.append("[]");
+                }
+                return b.toString();
+            case OBJECT:
+                return new String(buf, off, len).replace('/', '.');
+            default:
+                return null;
+        }
+    }
+
+    /**
+     * Returns the internal name of the class corresponding to this object or
+     * array type. The internal name of a class is its fully qualified name (as
+     * returned by Class.getName(), where '.' are replaced by '/'. This method
+     * should only be used for an object or array type.
+     *
+     * @return the internal name of the class corresponding to this object type.
+     */
+    public String getInternalName() {
+        return new String(buf, off, len);
+    }
+
+    /**
+     * Returns the argument types of methods of this type. This method should
+     * only be used for method types.
+     *
+     * @return the argument types of methods of this type.
+     */
+    public Type[] getArgumentTypes() {
+        return getArgumentTypes(getDescriptor());
+    }
+
+    /**
+     * Returns the return type of methods of this type. This method should only
+     * be used for method types.
+     *
+     * @return the return type of methods of this type.
+     */
+    public Type getReturnType() {
+        return getReturnType(getDescriptor());
+    }
+
+    /**
+     * Returns the size of the arguments and of the return value of methods of
+     * this type. This method should only be used for method types.
+     *
+     * @return the size of the arguments (plus one for the implicit this
+     *         argument), argSize, and the size of the return value, retSize,
+     *         packed into a single int i = <tt>(argSize << 2) | retSize</tt>
+     *         (argSize is therefore equal to <tt>i >> 2</tt>, and retSize to
+     *         <tt>i & 0x03</tt>).
+     */
+    public int getArgumentsAndReturnSizes() {
+        return getArgumentsAndReturnSizes(getDescriptor());
+    }
+
+    // ------------------------------------------------------------------------
+    // Conversion to type descriptors
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the descriptor corresponding to this Java type.
+     *
+     * @return the descriptor corresponding to this Java type.
+     */
+    public String getDescriptor() {
+        StringBuffer buf = new StringBuffer();
+        getDescriptor(buf);
+        return buf.toString();
+    }
+
+    /**
+     * Returns the descriptor corresponding to the given argument and return
+     * types.
+     *
+     * @param returnType the return type of the method.
+     * @param argumentTypes the argument types of the method.
+     * @return the descriptor corresponding to the given argument and return
+     *         types.
+     */
+    public static String getMethodDescriptor(
+        final Type returnType,
+        final Type... argumentTypes)
+    {
+        StringBuffer buf = new StringBuffer();
+        buf.append('(');
+        for (int i = 0; i < argumentTypes.length; ++i) {
+            argumentTypes[i].getDescriptor(buf);
+        }
+        buf.append(')');
+        returnType.getDescriptor(buf);
+        return buf.toString();
+    }
+
+    /**
+     * Appends the descriptor corresponding to this Java type to the given
+     * string buffer.
+     *
+     * @param buf the string buffer to which the descriptor must be appended.
+     */
+    private void getDescriptor(final StringBuffer buf) {
+        if (this.buf == null) {
+            // descriptor is in byte 3 of 'off' for primitive types (buf == null)
+            buf.append((char) ((off & 0xFF000000) >>> 24));
+        } else if (sort == OBJECT) {
+            buf.append('L');
+            buf.append(this.buf, off, len);
+            buf.append(';');
+        } else { // sort == ARRAY || sort == METHOD
+            buf.append(this.buf, off, len);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Direct conversion from classes to type descriptors,
+    // without intermediate Type objects
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the internal name of the given class. The internal name of a
+     * class is its fully qualified name, as returned by Class.getName(), where
+     * '.' are replaced by '/'.
+     *
+     * @param c an object or array class.
+     * @return the internal name of the given class.
+     */
+    public static String getInternalName(final Class<?> c) {
+        return c.getName().replace('.', '/');
+    }
+
+    /**
+     * Returns the descriptor corresponding to the given Java type.
+     *
+     * @param c an object class, a primitive class or an array class.
+     * @return the descriptor corresponding to the given class.
+     */
+    public static String getDescriptor(final Class<?> c) {
+        StringBuffer buf = new StringBuffer();
+        getDescriptor(buf, c);
+        return buf.toString();
+    }
+
+    /**
+     * Returns the descriptor corresponding to the given constructor.
+     *
+     * @param c a {@link Constructor Constructor} object.
+     * @return the descriptor of the given constructor.
+     */
+    public static String getConstructorDescriptor(final Constructor<?> c) {
+        Class<?>[] parameters = c.getParameterTypes();
+        StringBuffer buf = new StringBuffer();
+        buf.append('(');
+        for (int i = 0; i < parameters.length; ++i) {
+            getDescriptor(buf, parameters[i]);
+        }
+        return buf.append(")V").toString();
+    }
+
+    /**
+     * Returns the descriptor corresponding to the given method.
+     *
+     * @param m a {@link Method Method} object.
+     * @return the descriptor of the given method.
+     */
+    public static String getMethodDescriptor(final Method m) {
+        Class<?>[] parameters = m.getParameterTypes();
+        StringBuffer buf = new StringBuffer();
+        buf.append('(');
+        for (int i = 0; i < parameters.length; ++i) {
+            getDescriptor(buf, parameters[i]);
+        }
+        buf.append(')');
+        getDescriptor(buf, m.getReturnType());
+        return buf.toString();
+    }
+
+    /**
+     * Appends the descriptor of the given class to the given string buffer.
+     *
+     * @param buf the string buffer to which the descriptor must be appended.
+     * @param c the class whose descriptor must be computed.
+     */
+    private static void getDescriptor(final StringBuffer buf, final Class<?> c) {
+        Class<?> d = c;
+        while (true) {
+            if (d.isPrimitive()) {
+                char car;
+                if (d == Integer.TYPE) {
+                    car = 'I';
+                } else if (d == Void.TYPE) {
+                    car = 'V';
+                } else if (d == Boolean.TYPE) {
+                    car = 'Z';
+                } else if (d == Byte.TYPE) {
+                    car = 'B';
+                } else if (d == Character.TYPE) {
+                    car = 'C';
+                } else if (d == Short.TYPE) {
+                    car = 'S';
+                } else if (d == Double.TYPE) {
+                    car = 'D';
+                } else if (d == Float.TYPE) {
+                    car = 'F';
+                } else /* if (d == Long.TYPE) */{
+                    car = 'J';
+                }
+                buf.append(car);
+                return;
+            } else if (d.isArray()) {
+                buf.append('[');
+                d = d.getComponentType();
+            } else {
+                buf.append('L');
+                String name = d.getName();
+                int len = name.length();
+                for (int i = 0; i < len; ++i) {
+                    char car = name.charAt(i);
+                    buf.append(car == '.' ? '/' : car);
+                }
+                buf.append(';');
+                return;
+            }
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Corresponding size and opcodes
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the size of values of this type. This method must not be used for
+     * method types.
+     *
+     * @return the size of values of this type, i.e., 2 for <tt>long</tt> and
+     *         <tt>double</tt>, 0 for <tt>void</tt> and 1 otherwise.
+     */
+    public int getSize() {
+        // the size is in byte 0 of 'off' for primitive types (buf == null)
+        return buf == null ? (off & 0xFF) : 1;
+    }
+
+    /**
+     * Returns a JVM instruction opcode adapted to this Java type. This method
+     * must not be used for method types.
+     *
+     * @param opcode a JVM instruction opcode. This opcode must be one of ILOAD,
+     *        ISTORE, IALOAD, IASTORE, IADD, ISUB, IMUL, IDIV, IREM, INEG, ISHL,
+     *        ISHR, IUSHR, IAND, IOR, IXOR and IRETURN.
+     * @return an opcode that is similar to the given opcode, but adapted to
+     *         this Java type. For example, if this type is <tt>float</tt> and
+     *         <tt>opcode</tt> is IRETURN, this method returns FRETURN.
+     */
+    public int getOpcode(final int opcode) {
+        if (opcode == Opcodes.IALOAD || opcode == Opcodes.IASTORE) {
+            // the offset for IALOAD or IASTORE is in byte 1 of 'off' for
+            // primitive types (buf == null)
+            return opcode + (buf == null ? (off & 0xFF00) >> 8 : 4);
+        } else {
+            // the offset for other instructions is in byte 2 of 'off' for
+            // primitive types (buf == null)
+            return opcode + (buf == null ? (off & 0xFF0000) >> 16 : 4);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Equals, hashCode and toString
+    // ------------------------------------------------------------------------
+
+    /**
+     * Tests if the given object is equal to this type.
+     *
+     * @param o the object to be compared to this type.
+     * @return <tt>true</tt> if the given object is equal to this type.
+     */
+    @Override
+    public boolean equals(final Object o) {
+        if (this == o) {
+            return true;
+        }
+        if (!(o instanceof Type)) {
+            return false;
+        }
+        Type t = (Type) o;
+        if (sort != t.sort) {
+            return false;
+        }
+        if (sort >= ARRAY) {
+            if (len != t.len) {
+                return false;
+            }
+            for (int i = off, j = t.off, end = i + len; i < end; i++, j++) {
+                if (buf[i] != t.buf[j]) {
+                    return false;
+                }
+            }
+        }
+        return true;
+    }
+
+    /**
+     * Returns a hash code value for this type.
+     *
+     * @return a hash code value for this type.
+     */
+    @Override
+    public int hashCode() {
+        int hc = 13 * sort;
+        if (sort >= ARRAY) {
+            for (int i = off, end = i + len; i < end; i++) {
+                hc = 17 * (hc + buf[i]);
+            }
+        }
+        return hc;
+    }
+
+    /**
+     * Returns a string representation of this type.
+     *
+     * @return the descriptor of this type.
+     */
+    @Override
+    public String toString() {
+        return getDescriptor();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/AdviceAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,694 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link jdk.internal.org.objectweb.asm.MethodVisitor} to insert before, after and around
+ * advices in methods and constructors. <p> The behavior for constructors is
+ * like this: <ol>
+ *
+ * <li>as long as the INVOKESPECIAL for the object initialization has not been
+ * reached, every bytecode instruction is dispatched in the ctor code visitor</li>
+ *
+ * <li>when this one is reached, it is only added in the ctor code visitor and
+ * a JP invoke is added</li>
+ *
+ * <li>after that, only the other code visitor receives the instructions</li>
+ *
+ * </ol>
+ *
+ * @author Eugene Kuleshov
+ * @author Eric Bruneton
+ */
+public abstract class AdviceAdapter extends GeneratorAdapter implements Opcodes
+{
+
+    private static final Object THIS = new Object();
+
+    private static final Object OTHER = new Object();
+
+    protected int methodAccess;
+
+    protected String methodDesc;
+
+    private boolean constructor;
+
+    private boolean superInitialized;
+
+    private List<Object> stackFrame;
+
+    private Map<Label, List<Object>> branches;
+
+    /**
+     * Creates a new {@link AdviceAdapter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param mv the method visitor to which this adapter delegates calls.
+     * @param access the method's access flags (see {@link Opcodes}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     */
+    protected AdviceAdapter(
+        final int api,
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc)
+    {
+        super(api, mv, access, name, desc);
+        methodAccess = access;
+        methodDesc = desc;
+        constructor = "<init>".equals(name);
+    }
+
+    @Override
+    public void visitCode() {
+        mv.visitCode();
+        if (constructor) {
+            stackFrame = new ArrayList<Object>();
+            branches = new HashMap<Label, List<Object>>();
+        } else {
+            superInitialized = true;
+            onMethodEnter();
+        }
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        mv.visitLabel(label);
+        if (constructor && branches != null) {
+            List<Object> frame = branches.get(label);
+            if (frame != null) {
+                stackFrame = frame;
+                branches.remove(label);
+            }
+        }
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        if (constructor) {
+            int s;
+            switch (opcode) {
+                case RETURN: // empty stack
+                    onMethodExit(opcode);
+                    break;
+
+                case IRETURN: // 1 before n/a after
+                case FRETURN: // 1 before n/a after
+                case ARETURN: // 1 before n/a after
+                case ATHROW: // 1 before n/a after
+                    popValue();
+                    onMethodExit(opcode);
+                    break;
+
+                case LRETURN: // 2 before n/a after
+                case DRETURN: // 2 before n/a after
+                    popValue();
+                    popValue();
+                    onMethodExit(opcode);
+                    break;
+
+                case NOP:
+                case LALOAD: // remove 2 add 2
+                case DALOAD: // remove 2 add 2
+                case LNEG:
+                case DNEG:
+                case FNEG:
+                case INEG:
+                case L2D:
+                case D2L:
+                case F2I:
+                case I2B:
+                case I2C:
+                case I2S:
+                case I2F:
+                case ARRAYLENGTH:
+                    break;
+
+                case ACONST_NULL:
+                case ICONST_M1:
+                case ICONST_0:
+                case ICONST_1:
+                case ICONST_2:
+                case ICONST_3:
+                case ICONST_4:
+                case ICONST_5:
+                case FCONST_0:
+                case FCONST_1:
+                case FCONST_2:
+                case F2L: // 1 before 2 after
+                case F2D:
+                case I2L:
+                case I2D:
+                    pushValue(OTHER);
+                    break;
+
+                case LCONST_0:
+                case LCONST_1:
+                case DCONST_0:
+                case DCONST_1:
+                    pushValue(OTHER);
+                    pushValue(OTHER);
+                    break;
+
+                case IALOAD: // remove 2 add 1
+                case FALOAD: // remove 2 add 1
+                case AALOAD: // remove 2 add 1
+                case BALOAD: // remove 2 add 1
+                case CALOAD: // remove 2 add 1
+                case SALOAD: // remove 2 add 1
+                case POP:
+                case IADD:
+                case FADD:
+                case ISUB:
+                case LSHL: // 3 before 2 after
+                case LSHR: // 3 before 2 after
+                case LUSHR: // 3 before 2 after
+                case L2I: // 2 before 1 after
+                case L2F: // 2 before 1 after
+                case D2I: // 2 before 1 after
+                case D2F: // 2 before 1 after
+                case FSUB:
+                case FMUL:
+                case FDIV:
+                case FREM:
+                case FCMPL: // 2 before 1 after
+                case FCMPG: // 2 before 1 after
+                case IMUL:
+                case IDIV:
+                case IREM:
+                case ISHL:
+                case ISHR:
+                case IUSHR:
+                case IAND:
+                case IOR:
+                case IXOR:
+                case MONITORENTER:
+                case MONITOREXIT:
+                    popValue();
+                    break;
+
+                case POP2:
+                case LSUB:
+                case LMUL:
+                case LDIV:
+                case LREM:
+                case LADD:
+                case LAND:
+                case LOR:
+                case LXOR:
+                case DADD:
+                case DMUL:
+                case DSUB:
+                case DDIV:
+                case DREM:
+                    popValue();
+                    popValue();
+                    break;
+
+                case IASTORE:
+                case FASTORE:
+                case AASTORE:
+                case BASTORE:
+                case CASTORE:
+                case SASTORE:
+                case LCMP: // 4 before 1 after
+                case DCMPL:
+                case DCMPG:
+                    popValue();
+                    popValue();
+                    popValue();
+                    break;
+
+                case LASTORE:
+                case DASTORE:
+                    popValue();
+                    popValue();
+                    popValue();
+                    popValue();
+                    break;
+
+                case DUP:
+                    pushValue(peekValue());
+                    break;
+
+                case DUP_X1:
+                    s = stackFrame.size();
+                    stackFrame.add(s - 2, stackFrame.get(s - 1));
+                    break;
+
+                case DUP_X2:
+                    s = stackFrame.size();
+                    stackFrame.add(s - 3, stackFrame.get(s - 1));
+                    break;
+
+                case DUP2:
+                    s = stackFrame.size();
+                    stackFrame.add(s - 2, stackFrame.get(s - 1));
+                    stackFrame.add(s - 2, stackFrame.get(s - 1));
+                    break;
+
+                case DUP2_X1:
+                    s = stackFrame.size();
+                    stackFrame.add(s - 3, stackFrame.get(s - 1));
+                    stackFrame.add(s - 3, stackFrame.get(s - 1));
+                    break;
+
+                case DUP2_X2:
+                    s = stackFrame.size();
+                    stackFrame.add(s - 4, stackFrame.get(s - 1));
+                    stackFrame.add(s - 4, stackFrame.get(s - 1));
+                    break;
+
+                case SWAP:
+                    s = stackFrame.size();
+                    stackFrame.add(s - 2, stackFrame.get(s - 1));
+                    stackFrame.remove(s);
+                    break;
+            }
+        } else {
+            switch (opcode) {
+                case RETURN:
+                case IRETURN:
+                case FRETURN:
+                case ARETURN:
+                case LRETURN:
+                case DRETURN:
+                case ATHROW:
+                    onMethodExit(opcode);
+                    break;
+            }
+        }
+        mv.visitInsn(opcode);
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        super.visitVarInsn(opcode, var);
+        if (constructor) {
+            switch (opcode) {
+                case ILOAD:
+                case FLOAD:
+                    pushValue(OTHER);
+                    break;
+                case LLOAD:
+                case DLOAD:
+                    pushValue(OTHER);
+                    pushValue(OTHER);
+                    break;
+                case ALOAD:
+                    pushValue(var == 0 ? THIS : OTHER);
+                    break;
+                case ASTORE:
+                case ISTORE:
+                case FSTORE:
+                    popValue();
+                    break;
+                case LSTORE:
+                case DSTORE:
+                    popValue();
+                    popValue();
+                    break;
+            }
+        }
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitFieldInsn(opcode, owner, name, desc);
+        if (constructor) {
+            char c = desc.charAt(0);
+            boolean longOrDouble = c == 'J' || c == 'D';
+            switch (opcode) {
+                case GETSTATIC:
+                    pushValue(OTHER);
+                    if (longOrDouble) {
+                        pushValue(OTHER);
+                    }
+                    break;
+                case PUTSTATIC:
+                    popValue();
+                    if (longOrDouble) {
+                        popValue();
+                    }
+                    break;
+                case PUTFIELD:
+                    popValue();
+                    if (longOrDouble) {
+                        popValue();
+                        popValue();
+                    }
+                    break;
+                // case GETFIELD:
+                default:
+                    if (longOrDouble) {
+                        pushValue(OTHER);
+                    }
+            }
+        }
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        mv.visitIntInsn(opcode, operand);
+        if (constructor && opcode != NEWARRAY) {
+            pushValue(OTHER);
+        }
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        mv.visitLdcInsn(cst);
+        if (constructor) {
+            pushValue(OTHER);
+            if (cst instanceof Double || cst instanceof Long) {
+                pushValue(OTHER);
+            }
+        }
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        mv.visitMultiANewArrayInsn(desc, dims);
+        if (constructor) {
+            for (int i = 0; i < dims; i++) {
+                popValue();
+            }
+            pushValue(OTHER);
+        }
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        mv.visitTypeInsn(opcode, type);
+        // ANEWARRAY, CHECKCAST or INSTANCEOF don't change stack
+        if (constructor && opcode == NEW) {
+            pushValue(OTHER);
+        }
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitMethodInsn(opcode, owner, name, desc);
+        if (constructor) {
+            Type[] types = Type.getArgumentTypes(desc);
+            for (int i = 0; i < types.length; i++) {
+                popValue();
+                if (types[i].getSize() == 2) {
+                    popValue();
+                }
+            }
+            switch (opcode) {
+                // case INVOKESTATIC:
+                // break;
+
+                case INVOKEINTERFACE:
+                case INVOKEVIRTUAL:
+                    popValue(); // objectref
+                    break;
+
+                case INVOKESPECIAL:
+                    Object type = popValue(); // objectref
+                    if (type == THIS && !superInitialized) {
+                        onMethodEnter();
+                        superInitialized = true;
+                        // once super has been initialized it is no longer
+                        // necessary to keep track of stack state
+                        constructor = false;
+                    }
+                    break;
+            }
+
+            Type returnType = Type.getReturnType(desc);
+            if (returnType != Type.VOID_TYPE) {
+                pushValue(OTHER);
+                if (returnType.getSize() == 2) {
+                    pushValue(OTHER);
+                }
+            }
+        }
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+        if (constructor) {
+            Type[] types = Type.getArgumentTypes(desc);
+            for (int i = 0; i < types.length; i++) {
+                popValue();
+                if (types[i].getSize() == 2) {
+                    popValue();
+                }
+            }
+
+            Type returnType = Type.getReturnType(desc);
+            if (returnType != Type.VOID_TYPE) {
+                pushValue(OTHER);
+                if (returnType.getSize() == 2) {
+                    pushValue(OTHER);
+                }
+            }
+        }
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        mv.visitJumpInsn(opcode, label);
+        if (constructor) {
+            switch (opcode) {
+                case IFEQ:
+                case IFNE:
+                case IFLT:
+                case IFGE:
+                case IFGT:
+                case IFLE:
+                case IFNULL:
+                case IFNONNULL:
+                    popValue();
+                    break;
+
+                case IF_ICMPEQ:
+                case IF_ICMPNE:
+                case IF_ICMPLT:
+                case IF_ICMPGE:
+                case IF_ICMPGT:
+                case IF_ICMPLE:
+                case IF_ACMPEQ:
+                case IF_ACMPNE:
+                    popValue();
+                    popValue();
+                    break;
+
+                case JSR:
+                    pushValue(OTHER);
+                    break;
+            }
+            addBranch(label);
+        }
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        mv.visitLookupSwitchInsn(dflt, keys, labels);
+        if (constructor) {
+            popValue();
+            addBranches(dflt, labels);
+        }
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        mv.visitTableSwitchInsn(min, max, dflt, labels);
+        if (constructor) {
+            popValue();
+            addBranches(dflt, labels);
+        }
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        Label start,
+        Label end,
+        Label handler,
+        String type)
+    {
+        super.visitTryCatchBlock(start, end, handler, type);
+        if (constructor && !branches.containsKey(handler)) {
+            List<Object> stackFrame = new ArrayList<Object>();
+            stackFrame.add(OTHER);
+            branches.put(handler, stackFrame);
+        }
+    }
+
+    private void addBranches(final Label dflt, final Label[] labels) {
+        addBranch(dflt);
+        for (int i = 0; i < labels.length; i++) {
+            addBranch(labels[i]);
+        }
+    }
+
+    private void addBranch(final Label label) {
+        if (branches.containsKey(label)) {
+            return;
+        }
+        branches.put(label, new ArrayList<Object>(stackFrame));
+    }
+
+    private Object popValue() {
+        return stackFrame.remove(stackFrame.size() - 1);
+    }
+
+    private Object peekValue() {
+        return stackFrame.get(stackFrame.size() - 1);
+    }
+
+    private void pushValue(final Object o) {
+        stackFrame.add(o);
+    }
+
+    /**
+     * Called at the beginning of the method or after super class class call in
+     * the constructor. <br><br>
+     *
+     * <i>Custom code can use or change all the local variables, but should not
+     * change state of the stack.</i>
+     */
+    protected void onMethodEnter() {
+    }
+
+    /**
+     * Called before explicit exit from the method using either return or throw.
+     * Top element on the stack contains the return value or exception instance.
+     * For example:
+     *
+     * <pre>
+     *   public void onMethodExit(int opcode) {
+     *     if(opcode==RETURN) {
+     *         visitInsn(ACONST_NULL);
+     *     } else if(opcode==ARETURN || opcode==ATHROW) {
+     *         dup();
+     *     } else {
+     *         if(opcode==LRETURN || opcode==DRETURN) {
+     *             dup2();
+     *         } else {
+     *             dup();
+     *         }
+     *         box(Type.getReturnType(this.methodDesc));
+     *     }
+     *     visitIntInsn(SIPUSH, opcode);
+     *     visitMethodInsn(INVOKESTATIC, owner, "onExit", "(Ljava/lang/Object;I)V");
+     *   }
+     *
+     *   // an actual call back method
+     *   public static void onExit(Object param, int opcode) {
+     *     ...
+     * </pre>
+     *
+     * <br><br>
+     *
+     * <i>Custom code can use or change all the local variables, but should not
+     * change state of the stack.</i>
+     *
+     * @param opcode one of the RETURN, IRETURN, FRETURN, ARETURN, LRETURN,
+     *        DRETURN or ATHROW
+     *
+     */
+    protected void onMethodExit(int opcode) {
+    }
+
+    // TODO onException, onMethodCall
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/AnalyzerAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,975 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link MethodVisitor} that keeps track of stack map frame changes between
+ * {@link #visitFrame(int, int, Object[], int, Object[]) visitFrame} calls. This
+ * adapter must be used with the
+ * {@link jdk.internal.org.objectweb.asm.ClassReader#EXPAND_FRAMES} option. Each visit<i>X</i>
+ * instruction delegates to the next visitor in the chain, if any, and then
+ * simulates the effect of this instruction on the stack map frame, represented
+ * by {@link #locals} and {@link #stack}. The next visitor in the chain can get
+ * the state of the stack map frame <i>before</i> each instruction by reading
+ * the value of these fields in its visit<i>X</i> methods (this requires a
+ * reference to the AnalyzerAdapter that is before it in the chain).
+ * If this adapter is used with a class that does not contain stack map table
+ * attributes (i.e., pre Java 6 classes) then this adapter may not be able to
+ * compute the stack map frame for each instruction. In this case no exception
+ * is thrown but the {@link #locals} and {@link #stack} fields will be null for
+ * these instructions.
+ *
+ * @author Eric Bruneton
+ */
+public class AnalyzerAdapter extends MethodVisitor {
+
+    /**
+     * <code>List</code> of the local variable slots for current execution
+     * frame. Primitive types are represented by {@link Opcodes#TOP},
+     * {@link Opcodes#INTEGER}, {@link Opcodes#FLOAT}, {@link Opcodes#LONG},
+     * {@link Opcodes#DOUBLE},{@link Opcodes#NULL} or
+     * {@link Opcodes#UNINITIALIZED_THIS} (long and double are represented by a
+     * two elements, the second one being TOP). Reference types are represented
+     * by String objects (representing internal names), and uninitialized types
+     * by Label objects (this label designates the NEW instruction that created
+     * this uninitialized value). This field is <tt>null</tt> for unreacheable
+     * instructions.
+     */
+    public List<Object> locals;
+
+    /**
+     * <code>List</code> of the operand stack slots for current execution
+     * frame. Primitive types are represented by {@link Opcodes#TOP},
+     * {@link Opcodes#INTEGER}, {@link Opcodes#FLOAT}, {@link Opcodes#LONG},
+     * {@link Opcodes#DOUBLE},{@link Opcodes#NULL} or
+     * {@link Opcodes#UNINITIALIZED_THIS} (long and double are represented by a
+     * two elements, the second one being TOP). Reference types are represented
+     * by String objects (representing internal names), and uninitialized types
+     * by Label objects (this label designates the NEW instruction that created
+     * this uninitialized value). This field is <tt>null</tt> for unreacheable
+     * instructions.
+     */
+    public List<Object> stack;
+
+    /**
+     * The labels that designate the next instruction to be visited. May be
+     * <tt>null</tt>.
+     */
+    private List<Label> labels;
+
+    /**
+     * Information about uninitialized types in the current execution frame.
+     * This map associates internal names to Label objects. Each label
+     * designates a NEW instruction that created the currently uninitialized
+     * types, and the associated internal name represents the NEW operand, i.e.
+     * the final, initialized type value.
+     */
+    public Map<Object,Object> uninitializedTypes;
+
+    /**
+     * The maximum stack size of this method.
+     */
+    private int maxStack;
+
+    /**
+     * The maximum number of local variables of this method.
+     */
+    private int maxLocals;
+
+    /**
+     * The owner's class name.
+     */
+    private String owner;
+
+    /**
+     * Creates a new {@link AnalyzerAdapter}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #AnalyzerAdapter(int, String, int, String, String, MethodVisitor)}
+     * version.
+     *
+     * @param owner the owner's class name.
+     * @param access the method's access flags (see {@link Opcodes}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param mv the method visitor to which this adapter delegates calls. May
+     *        be <tt>null</tt>.
+     */
+    public AnalyzerAdapter(
+        final String owner,
+        final int access,
+        final String name,
+        final String desc,
+        final MethodVisitor mv)
+    {
+        this(Opcodes.ASM4, owner, access, name, desc, mv);
+    }
+
+    /**
+     * Creates a new {@link AnalyzerAdapter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param owner the owner's class name.
+     * @param access the method's access flags (see {@link Opcodes}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param mv the method visitor to which this adapter delegates calls. May
+     *        be <tt>null</tt>.
+     */
+    protected AnalyzerAdapter(
+        final int api,
+        final String owner,
+        final int access,
+        final String name,
+        final String desc,
+        final MethodVisitor mv)
+    {
+        super(api, mv);
+        this.owner = owner;
+        locals = new ArrayList<Object>();
+        stack = new ArrayList<Object>();
+        uninitializedTypes = new HashMap<Object, Object>();
+
+        if ((access & Opcodes.ACC_STATIC) == 0) {
+            if ("<init>".equals(name)) {
+                locals.add(Opcodes.UNINITIALIZED_THIS);
+            } else {
+                locals.add(owner);
+            }
+        }
+        Type[] types = Type.getArgumentTypes(desc);
+        for (int i = 0; i < types.length; ++i) {
+            Type type = types[i];
+            switch (type.getSort()) {
+                case Type.BOOLEAN:
+                case Type.CHAR:
+                case Type.BYTE:
+                case Type.SHORT:
+                case Type.INT:
+                    locals.add(Opcodes.INTEGER);
+                    break;
+                case Type.FLOAT:
+                    locals.add(Opcodes.FLOAT);
+                    break;
+                case Type.LONG:
+                    locals.add(Opcodes.LONG);
+                    locals.add(Opcodes.TOP);
+                    break;
+                case Type.DOUBLE:
+                    locals.add(Opcodes.DOUBLE);
+                    locals.add(Opcodes.TOP);
+                    break;
+                case Type.ARRAY:
+                    locals.add(types[i].getDescriptor());
+                    break;
+                // case Type.OBJECT:
+                default:
+                    locals.add(types[i].getInternalName());
+            }
+        }
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        if (type != Opcodes.F_NEW) { // uncompressed frame
+            throw new IllegalStateException("ClassReader.accept() should be called with EXPAND_FRAMES flag");
+        }
+
+        if (mv != null) {
+            mv.visitFrame(type, nLocal, local, nStack, stack);
+        }
+
+        if (this.locals != null) {
+            this.locals.clear();
+            this.stack.clear();
+        } else {
+            this.locals = new ArrayList<Object>();
+            this.stack = new ArrayList<Object>();
+        }
+        visitFrameTypes(nLocal, local, this.locals);
+        visitFrameTypes(nStack, stack, this.stack);
+        maxStack = Math.max(maxStack, this.stack.size());
+    }
+
+    private static void visitFrameTypes(
+        final int n,
+        final Object[] types,
+        final List<Object> result)
+    {
+        for (int i = 0; i < n; ++i) {
+            Object type = types[i];
+            result.add(type);
+            if (type == Opcodes.LONG || type == Opcodes.DOUBLE) {
+                result.add(Opcodes.TOP);
+            }
+        }
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        if (mv != null) {
+            mv.visitInsn(opcode);
+        }
+        execute(opcode, 0, null);
+        if ((opcode >= Opcodes.IRETURN && opcode <= Opcodes.RETURN)
+                || opcode == Opcodes.ATHROW)
+        {
+            this.locals = null;
+            this.stack = null;
+        }
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        if (mv != null) {
+            mv.visitIntInsn(opcode, operand);
+        }
+        execute(opcode, operand, null);
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        if (mv != null) {
+            mv.visitVarInsn(opcode, var);
+        }
+        execute(opcode, var, null);
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        if (opcode == Opcodes.NEW) {
+            if (labels == null) {
+                Label l = new Label();
+                labels = new ArrayList<Label>(3);
+                labels.add(l);
+                if (mv != null) {
+                    mv.visitLabel(l);
+                }
+            }
+            for (int i = 0; i < labels.size(); ++i) {
+                uninitializedTypes.put(labels.get(i), type);
+            }
+        }
+        if (mv != null) {
+            mv.visitTypeInsn(opcode, type);
+        }
+        execute(opcode, 0, type);
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        if (mv != null) {
+            mv.visitFieldInsn(opcode, owner, name, desc);
+        }
+        execute(opcode, 0, desc);
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        if (mv != null) {
+            mv.visitMethodInsn(opcode, owner, name, desc);
+        }
+        if (this.locals == null) {
+            labels = null;
+            return;
+        }
+        pop(desc);
+        if (opcode != Opcodes.INVOKESTATIC) {
+            Object t = pop();
+            if (opcode == Opcodes.INVOKESPECIAL && name.charAt(0) == '<') {
+                Object u;
+                if (t == Opcodes.UNINITIALIZED_THIS) {
+                    u = this.owner;
+                } else {
+                    u = uninitializedTypes.get(t);
+                }
+                for (int i = 0; i < locals.size(); ++i) {
+                    if (locals.get(i) == t) {
+                        locals.set(i, u);
+                    }
+                }
+                for (int i = 0; i < stack.size(); ++i) {
+                    if (stack.get(i) == t) {
+                        stack.set(i, u);
+                    }
+                }
+            }
+        }
+        pushDesc(desc);
+        labels = null;
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        if (mv != null) {
+            mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+        }
+        if (this.locals == null) {
+            labels = null;
+            return;
+        }
+        pop(desc);
+        pushDesc(desc);
+        labels = null;
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        if (mv != null) {
+            mv.visitJumpInsn(opcode, label);
+        }
+        execute(opcode, 0, null);
+        if (opcode == Opcodes.GOTO) {
+            this.locals = null;
+            this.stack = null;
+        }
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        if (mv != null) {
+            mv.visitLabel(label);
+        }
+        if (labels == null) {
+            labels = new ArrayList<Label>(3);
+        }
+        labels.add(label);
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        if (mv != null) {
+            mv.visitLdcInsn(cst);
+        }
+        if (this.locals == null) {
+            labels = null;
+            return;
+        }
+        if (cst instanceof Integer) {
+            push(Opcodes.INTEGER);
+        } else if (cst instanceof Long) {
+            push(Opcodes.LONG);
+            push(Opcodes.TOP);
+        } else if (cst instanceof Float) {
+            push(Opcodes.FLOAT);
+        } else if (cst instanceof Double) {
+            push(Opcodes.DOUBLE);
+            push(Opcodes.TOP);
+        } else if (cst instanceof String) {
+            push("java/lang/String");
+        } else if (cst instanceof Type) {
+            int sort = ((Type) cst).getSort();
+            if (sort == Type.OBJECT || sort == Type.ARRAY) {
+                push("java/lang/Class");
+            } else if (sort == Type.METHOD) {
+                push("java/lang/invoke/MethodType");
+            } else {
+                throw new IllegalArgumentException();
+            }
+        } else if (cst instanceof Handle) {
+            push("java/lang/invoke/MethodHandle");
+        } else {
+            throw new IllegalArgumentException();
+        }
+        labels = null;
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        if (mv != null) {
+            mv.visitIincInsn(var, increment);
+        }
+        execute(Opcodes.IINC, var, null);
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        if (mv != null) {
+            mv.visitTableSwitchInsn(min, max, dflt, labels);
+        }
+        execute(Opcodes.TABLESWITCH, 0, null);
+        this.locals = null;
+        this.stack = null;
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        if (mv != null) {
+            mv.visitLookupSwitchInsn(dflt, keys, labels);
+        }
+        execute(Opcodes.LOOKUPSWITCH, 0, null);
+        this.locals = null;
+        this.stack = null;
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        if (mv != null) {
+            mv.visitMultiANewArrayInsn(desc, dims);
+        }
+        execute(Opcodes.MULTIANEWARRAY, dims, desc);
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        if (mv != null) {
+            this.maxStack = Math.max(this.maxStack, maxStack);
+            this.maxLocals = Math.max(this.maxLocals, maxLocals);
+            mv.visitMaxs(this.maxStack, this.maxLocals);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+
+    private Object get(final int local) {
+        maxLocals = Math.max(maxLocals, local);
+        return local < locals.size() ? locals.get(local) : Opcodes.TOP;
+    }
+
+    private void set(final int local, final Object type) {
+        maxLocals = Math.max(maxLocals, local);
+        while (local >= locals.size()) {
+            locals.add(Opcodes.TOP);
+        }
+        locals.set(local, type);
+    }
+
+    private void push(final Object type) {
+        stack.add(type);
+        maxStack = Math.max(maxStack, stack.size());
+    }
+
+    private void pushDesc(final String desc) {
+        int index = desc.charAt(0) == '(' ? desc.indexOf(')') + 1 : 0;
+        switch (desc.charAt(index)) {
+            case 'V':
+                return;
+            case 'Z':
+            case 'C':
+            case 'B':
+            case 'S':
+            case 'I':
+                push(Opcodes.INTEGER);
+                return;
+            case 'F':
+                push(Opcodes.FLOAT);
+                return;
+            case 'J':
+                push(Opcodes.LONG);
+                push(Opcodes.TOP);
+                return;
+            case 'D':
+                push(Opcodes.DOUBLE);
+                push(Opcodes.TOP);
+                return;
+            case '[':
+                if (index == 0) {
+                    push(desc);
+                } else {
+                    push(desc.substring(index, desc.length()));
+                }
+                break;
+            // case 'L':
+            default:
+                if (index == 0) {
+                    push(desc.substring(1, desc.length() - 1));
+                } else {
+                    push(desc.substring(index + 1, desc.length() - 1));
+                }
+        }
+    }
+
+    private Object pop() {
+        return stack.remove(stack.size() - 1);
+    }
+
+    private void pop(final int n) {
+        int size = stack.size();
+        int end = size - n;
+        for (int i = size - 1; i >= end; --i) {
+            stack.remove(i);
+        }
+    }
+
+    private void pop(final String desc) {
+        char c = desc.charAt(0);
+        if (c == '(') {
+            int n = 0;
+            Type[] types = Type.getArgumentTypes(desc);
+            for (int i = 0; i < types.length; ++i) {
+                n += types[i].getSize();
+            }
+            pop(n);
+        } else if (c == 'J' || c == 'D') {
+            pop(2);
+        } else {
+            pop(1);
+        }
+    }
+
+    private void execute(final int opcode, final int iarg, final String sarg) {
+        if (this.locals == null) {
+            labels = null;
+            return;
+        }
+        Object t1, t2, t3, t4;
+        switch (opcode) {
+            case Opcodes.NOP:
+            case Opcodes.INEG:
+            case Opcodes.LNEG:
+            case Opcodes.FNEG:
+            case Opcodes.DNEG:
+            case Opcodes.I2B:
+            case Opcodes.I2C:
+            case Opcodes.I2S:
+            case Opcodes.GOTO:
+            case Opcodes.RETURN:
+                break;
+            case Opcodes.ACONST_NULL:
+                push(Opcodes.NULL);
+                break;
+            case Opcodes.ICONST_M1:
+            case Opcodes.ICONST_0:
+            case Opcodes.ICONST_1:
+            case Opcodes.ICONST_2:
+            case Opcodes.ICONST_3:
+            case Opcodes.ICONST_4:
+            case Opcodes.ICONST_5:
+            case Opcodes.BIPUSH:
+            case Opcodes.SIPUSH:
+                push(Opcodes.INTEGER);
+                break;
+            case Opcodes.LCONST_0:
+            case Opcodes.LCONST_1:
+                push(Opcodes.LONG);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.FCONST_0:
+            case Opcodes.FCONST_1:
+            case Opcodes.FCONST_2:
+                push(Opcodes.FLOAT);
+                break;
+            case Opcodes.DCONST_0:
+            case Opcodes.DCONST_1:
+                push(Opcodes.DOUBLE);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.ILOAD:
+            case Opcodes.FLOAD:
+            case Opcodes.ALOAD:
+                push(get(iarg));
+                break;
+            case Opcodes.LLOAD:
+            case Opcodes.DLOAD:
+                push(get(iarg));
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.IALOAD:
+            case Opcodes.BALOAD:
+            case Opcodes.CALOAD:
+            case Opcodes.SALOAD:
+                pop(2);
+                push(Opcodes.INTEGER);
+                break;
+            case Opcodes.LALOAD:
+            case Opcodes.D2L:
+                pop(2);
+                push(Opcodes.LONG);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.FALOAD:
+                pop(2);
+                push(Opcodes.FLOAT);
+                break;
+            case Opcodes.DALOAD:
+            case Opcodes.L2D:
+                pop(2);
+                push(Opcodes.DOUBLE);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.AALOAD:
+                pop(1);
+                t1 = pop();
+                if (t1 instanceof String) {
+                    pushDesc(((String) t1).substring(1));
+                } else {
+                    push("java/lang/Object");
+                }
+                break;
+            case Opcodes.ISTORE:
+            case Opcodes.FSTORE:
+            case Opcodes.ASTORE:
+                t1 = pop();
+                set(iarg, t1);
+                if (iarg > 0) {
+                    t2 = get(iarg - 1);
+                    if (t2 == Opcodes.LONG || t2 == Opcodes.DOUBLE) {
+                        set(iarg - 1, Opcodes.TOP);
+                    }
+                }
+                break;
+            case Opcodes.LSTORE:
+            case Opcodes.DSTORE:
+                pop(1);
+                t1 = pop();
+                set(iarg, t1);
+                set(iarg + 1, Opcodes.TOP);
+                if (iarg > 0) {
+                    t2 = get(iarg - 1);
+                    if (t2 == Opcodes.LONG || t2 == Opcodes.DOUBLE) {
+                        set(iarg - 1, Opcodes.TOP);
+                    }
+                }
+                break;
+            case Opcodes.IASTORE:
+            case Opcodes.BASTORE:
+            case Opcodes.CASTORE:
+            case Opcodes.SASTORE:
+            case Opcodes.FASTORE:
+            case Opcodes.AASTORE:
+                pop(3);
+                break;
+            case Opcodes.LASTORE:
+            case Opcodes.DASTORE:
+                pop(4);
+                break;
+            case Opcodes.POP:
+            case Opcodes.IFEQ:
+            case Opcodes.IFNE:
+            case Opcodes.IFLT:
+            case Opcodes.IFGE:
+            case Opcodes.IFGT:
+            case Opcodes.IFLE:
+            case Opcodes.IRETURN:
+            case Opcodes.FRETURN:
+            case Opcodes.ARETURN:
+            case Opcodes.TABLESWITCH:
+            case Opcodes.LOOKUPSWITCH:
+            case Opcodes.ATHROW:
+            case Opcodes.MONITORENTER:
+            case Opcodes.MONITOREXIT:
+            case Opcodes.IFNULL:
+            case Opcodes.IFNONNULL:
+                pop(1);
+                break;
+            case Opcodes.POP2:
+            case Opcodes.IF_ICMPEQ:
+            case Opcodes.IF_ICMPNE:
+            case Opcodes.IF_ICMPLT:
+            case Opcodes.IF_ICMPGE:
+            case Opcodes.IF_ICMPGT:
+            case Opcodes.IF_ICMPLE:
+            case Opcodes.IF_ACMPEQ:
+            case Opcodes.IF_ACMPNE:
+            case Opcodes.LRETURN:
+            case Opcodes.DRETURN:
+                pop(2);
+                break;
+            case Opcodes.DUP:
+                t1 = pop();
+                push(t1);
+                push(t1);
+                break;
+            case Opcodes.DUP_X1:
+                t1 = pop();
+                t2 = pop();
+                push(t1);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP_X2:
+                t1 = pop();
+                t2 = pop();
+                t3 = pop();
+                push(t1);
+                push(t3);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP2:
+                t1 = pop();
+                t2 = pop();
+                push(t2);
+                push(t1);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP2_X1:
+                t1 = pop();
+                t2 = pop();
+                t3 = pop();
+                push(t2);
+                push(t1);
+                push(t3);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.DUP2_X2:
+                t1 = pop();
+                t2 = pop();
+                t3 = pop();
+                t4 = pop();
+                push(t2);
+                push(t1);
+                push(t4);
+                push(t3);
+                push(t2);
+                push(t1);
+                break;
+            case Opcodes.SWAP:
+                t1 = pop();
+                t2 = pop();
+                push(t1);
+                push(t2);
+                break;
+            case Opcodes.IADD:
+            case Opcodes.ISUB:
+            case Opcodes.IMUL:
+            case Opcodes.IDIV:
+            case Opcodes.IREM:
+            case Opcodes.IAND:
+            case Opcodes.IOR:
+            case Opcodes.IXOR:
+            case Opcodes.ISHL:
+            case Opcodes.ISHR:
+            case Opcodes.IUSHR:
+            case Opcodes.L2I:
+            case Opcodes.D2I:
+            case Opcodes.FCMPL:
+            case Opcodes.FCMPG:
+                pop(2);
+                push(Opcodes.INTEGER);
+                break;
+            case Opcodes.LADD:
+            case Opcodes.LSUB:
+            case Opcodes.LMUL:
+            case Opcodes.LDIV:
+            case Opcodes.LREM:
+            case Opcodes.LAND:
+            case Opcodes.LOR:
+            case Opcodes.LXOR:
+                pop(4);
+                push(Opcodes.LONG);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.FADD:
+            case Opcodes.FSUB:
+            case Opcodes.FMUL:
+            case Opcodes.FDIV:
+            case Opcodes.FREM:
+            case Opcodes.L2F:
+            case Opcodes.D2F:
+                pop(2);
+                push(Opcodes.FLOAT);
+                break;
+            case Opcodes.DADD:
+            case Opcodes.DSUB:
+            case Opcodes.DMUL:
+            case Opcodes.DDIV:
+            case Opcodes.DREM:
+                pop(4);
+                push(Opcodes.DOUBLE);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.LSHL:
+            case Opcodes.LSHR:
+            case Opcodes.LUSHR:
+                pop(3);
+                push(Opcodes.LONG);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.IINC:
+                set(iarg, Opcodes.INTEGER);
+                break;
+            case Opcodes.I2L:
+            case Opcodes.F2L:
+                pop(1);
+                push(Opcodes.LONG);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.I2F:
+                pop(1);
+                push(Opcodes.FLOAT);
+                break;
+            case Opcodes.I2D:
+            case Opcodes.F2D:
+                pop(1);
+                push(Opcodes.DOUBLE);
+                push(Opcodes.TOP);
+                break;
+            case Opcodes.F2I:
+            case Opcodes.ARRAYLENGTH:
+            case Opcodes.INSTANCEOF:
+                pop(1);
+                push(Opcodes.INTEGER);
+                break;
+            case Opcodes.LCMP:
+            case Opcodes.DCMPL:
+            case Opcodes.DCMPG:
+                pop(4);
+                push(Opcodes.INTEGER);
+                break;
+            case Opcodes.JSR:
+            case Opcodes.RET:
+                throw new RuntimeException("JSR/RET are not supported");
+            case Opcodes.GETSTATIC:
+                pushDesc(sarg);
+                break;
+            case Opcodes.PUTSTATIC:
+                pop(sarg);
+                break;
+            case Opcodes.GETFIELD:
+                pop(1);
+                pushDesc(sarg);
+                break;
+            case Opcodes.PUTFIELD:
+                pop(sarg);
+                pop();
+                break;
+            case Opcodes.NEW:
+                push(labels.get(0));
+                break;
+            case Opcodes.NEWARRAY:
+                pop();
+                switch (iarg) {
+                    case Opcodes.T_BOOLEAN:
+                        pushDesc("[Z");
+                        break;
+                    case Opcodes.T_CHAR:
+                        pushDesc("[C");
+                        break;
+                    case Opcodes.T_BYTE:
+                        pushDesc("[B");
+                        break;
+                    case Opcodes.T_SHORT:
+                        pushDesc("[S");
+                        break;
+                    case Opcodes.T_INT:
+                        pushDesc("[I");
+                        break;
+                    case Opcodes.T_FLOAT:
+                        pushDesc("[F");
+                        break;
+                    case Opcodes.T_DOUBLE:
+                        pushDesc("[D");
+                        break;
+                    // case Opcodes.T_LONG:
+                    default:
+                        pushDesc("[J");
+                        break;
+                }
+                break;
+            case Opcodes.ANEWARRAY:
+                pop();
+                pushDesc("[" + Type.getObjectType(sarg));
+                break;
+            case Opcodes.CHECKCAST:
+                pop();
+                pushDesc(Type.getObjectType(sarg).getDescriptor());
+                break;
+            // case Opcodes.MULTIANEWARRAY:
+            default:
+                pop(iarg);
+                pushDesc(sarg);
+                break;
+        }
+        labels = null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/CodeSizeEvaluator.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,265 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link MethodVisitor} that can be used to approximate method size.
+ *
+ * @author Eugene Kuleshov
+ */
+public class CodeSizeEvaluator extends MethodVisitor implements Opcodes {
+
+    private int minSize;
+
+    private int maxSize;
+
+    public CodeSizeEvaluator(final MethodVisitor mv) {
+        this(Opcodes.ASM4, mv);
+    }
+
+    protected CodeSizeEvaluator(final int api, final MethodVisitor mv) {
+        super(api, mv);
+    }
+
+    public int getMinSize() {
+        return this.minSize;
+    }
+
+    public int getMaxSize() {
+        return this.maxSize;
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        minSize += 1;
+        maxSize += 1;
+        if (mv != null) {
+            mv.visitInsn(opcode);
+        }
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        if (opcode == SIPUSH) {
+            minSize += 3;
+            maxSize += 3;
+        } else {
+            minSize += 2;
+            maxSize += 2;
+        }
+        if (mv != null) {
+            mv.visitIntInsn(opcode, operand);
+        }
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        if (var < 4 && opcode != RET) {
+            minSize += 1;
+            maxSize += 1;
+        } else if (var >= 256) {
+            minSize += 4;
+            maxSize += 4;
+        } else {
+            minSize += 2;
+            maxSize += 2;
+        }
+        if (mv != null) {
+            mv.visitVarInsn(opcode, var);
+        }
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        minSize += 3;
+        maxSize += 3;
+        if (mv != null) {
+            mv.visitTypeInsn(opcode, type);
+        }
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        minSize += 3;
+        maxSize += 3;
+        if (mv != null) {
+            mv.visitFieldInsn(opcode, owner, name, desc);
+        }
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        if (opcode == INVOKEINTERFACE) {
+            minSize += 5;
+            maxSize += 5;
+        } else {
+            minSize += 3;
+            maxSize += 3;
+        }
+        if (mv != null) {
+            mv.visitMethodInsn(opcode, owner, name, desc);
+        }
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        minSize += 5;
+        maxSize += 5;
+        if (mv != null) {
+            mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+        }
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        minSize += 3;
+        if (opcode == GOTO || opcode == JSR) {
+            maxSize += 5;
+        } else {
+            maxSize += 8;
+        }
+        if (mv != null) {
+            mv.visitJumpInsn(opcode, label);
+        }
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        if (cst instanceof Long || cst instanceof Double) {
+            minSize += 3;
+            maxSize += 3;
+        } else {
+            minSize += 2;
+            maxSize += 3;
+        }
+        if (mv != null) {
+            mv.visitLdcInsn(cst);
+        }
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        if (var > 255 || increment > 127 || increment < -128) {
+            minSize += 6;
+            maxSize += 6;
+        } else {
+            minSize += 3;
+            maxSize += 3;
+        }
+        if (mv != null) {
+            mv.visitIincInsn(var, increment);
+        }
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        minSize += 13 + labels.length * 4;
+        maxSize += 16 + labels.length * 4;
+        if (mv != null) {
+            mv.visitTableSwitchInsn(min, max, dflt, labels);
+        }
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        minSize += 9 + keys.length * 8;
+        maxSize += 12 + keys.length * 8;
+        if (mv != null) {
+            mv.visitLookupSwitchInsn(dflt, keys, labels);
+        }
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        minSize += 4;
+        maxSize += 4;
+        if (mv != null) {
+            mv.visitMultiANewArrayInsn(desc, dims);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/GeneratorAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1578 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link jdk.internal.org.objectweb.asm.MethodVisitor} with convenient methods to generate
+ * code. For example, using this adapter, the class below
+ *
+ * <pre>
+ * public class Example {
+ *     public static void main(String[] args) {
+ *         System.out.println(&quot;Hello world!&quot;);
+ *     }
+ * }
+ * </pre>
+ *
+ * can be generated as follows:
+ *
+ * <pre>
+ * ClassWriter cw = new ClassWriter(true);
+ * cw.visit(V1_1, ACC_PUBLIC, &quot;Example&quot;, null, &quot;java/lang/Object&quot;, null);
+ *
+ * Method m = Method.getMethod(&quot;void &lt;init&gt; ()&quot;);
+ * GeneratorAdapter mg = new GeneratorAdapter(ACC_PUBLIC, m, null, null, cw);
+ * mg.loadThis();
+ * mg.invokeConstructor(Type.getType(Object.class), m);
+ * mg.returnValue();
+ * mg.endMethod();
+ *
+ * m = Method.getMethod(&quot;void main (String[])&quot;);
+ * mg = new GeneratorAdapter(ACC_PUBLIC + ACC_STATIC, m, null, null, cw);
+ * mg.getStatic(Type.getType(System.class), &quot;out&quot;, Type.getType(PrintStream.class));
+ * mg.push(&quot;Hello world!&quot;);
+ * mg.invokeVirtual(Type.getType(PrintStream.class), Method.getMethod(&quot;void println (String)&quot;));
+ * mg.returnValue();
+ * mg.endMethod();
+ *
+ * cw.visitEnd();
+ * </pre>
+ *
+ * @author Juozas Baliuka
+ * @author Chris Nokleberg
+ * @author Eric Bruneton
+ * @author Prashant Deva
+ */
+public class GeneratorAdapter extends LocalVariablesSorter {
+
+    private static final String CLDESC = "Ljava/lang/Class;";
+
+    private static final Type BYTE_TYPE = Type.getObjectType("java/lang/Byte");
+
+    private static final Type BOOLEAN_TYPE = Type.getObjectType("java/lang/Boolean");
+
+    private static final Type SHORT_TYPE = Type.getObjectType("java/lang/Short");
+
+    private static final Type CHARACTER_TYPE = Type.getObjectType("java/lang/Character");
+
+    private static final Type INTEGER_TYPE = Type.getObjectType("java/lang/Integer");
+
+    private static final Type FLOAT_TYPE = Type.getObjectType("java/lang/Float");
+
+    private static final Type LONG_TYPE = Type.getObjectType("java/lang/Long");
+
+    private static final Type DOUBLE_TYPE = Type.getObjectType("java/lang/Double");
+
+    private static final Type NUMBER_TYPE = Type.getObjectType("java/lang/Number");
+
+    private static final Type OBJECT_TYPE = Type.getObjectType("java/lang/Object");
+
+    private static final Method BOOLEAN_VALUE = Method.getMethod("boolean booleanValue()");
+
+    private static final Method CHAR_VALUE = Method.getMethod("char charValue()");
+
+    private static final Method INT_VALUE = Method.getMethod("int intValue()");
+
+    private static final Method FLOAT_VALUE = Method.getMethod("float floatValue()");
+
+    private static final Method LONG_VALUE = Method.getMethod("long longValue()");
+
+    private static final Method DOUBLE_VALUE = Method.getMethod("double doubleValue()");
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int ADD = Opcodes.IADD;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int SUB = Opcodes.ISUB;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int MUL = Opcodes.IMUL;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int DIV = Opcodes.IDIV;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int REM = Opcodes.IREM;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int NEG = Opcodes.INEG;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int SHL = Opcodes.ISHL;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int SHR = Opcodes.ISHR;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int USHR = Opcodes.IUSHR;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int AND = Opcodes.IAND;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int OR = Opcodes.IOR;
+
+    /**
+     * Constant for the {@link #math math} method.
+     */
+    public static final int XOR = Opcodes.IXOR;
+
+    /**
+     * Constant for the {@link #ifCmp ifCmp} method.
+     */
+    public static final int EQ = Opcodes.IFEQ;
+
+    /**
+     * Constant for the {@link #ifCmp ifCmp} method.
+     */
+    public static final int NE = Opcodes.IFNE;
+
+    /**
+     * Constant for the {@link #ifCmp ifCmp} method.
+     */
+    public static final int LT = Opcodes.IFLT;
+
+    /**
+     * Constant for the {@link #ifCmp ifCmp} method.
+     */
+    public static final int GE = Opcodes.IFGE;
+
+    /**
+     * Constant for the {@link #ifCmp ifCmp} method.
+     */
+    public static final int GT = Opcodes.IFGT;
+
+    /**
+     * Constant for the {@link #ifCmp ifCmp} method.
+     */
+    public static final int LE = Opcodes.IFLE;
+
+    /**
+     * Access flags of the method visited by this adapter.
+     */
+    private final int access;
+
+    /**
+     * Return type of the method visited by this adapter.
+     */
+    private final Type returnType;
+
+    /**
+     * Argument types of the method visited by this adapter.
+     */
+    private final Type[] argumentTypes;
+
+    /**
+     * Types of the local variables of the method visited by this adapter.
+     */
+    private final List<Type> localTypes = new ArrayList<Type>();
+
+    /**
+     * Creates a new {@link GeneratorAdapter}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #GeneratorAdapter(int, MethodVisitor, int, String, String)}
+     * version.
+     *
+     * @param mv the method visitor to which this adapter delegates calls.
+     * @param access the method's access flags (see {@link Opcodes}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     */
+    public GeneratorAdapter(
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc)
+    {
+        this(Opcodes.ASM4, mv, access, name, desc);
+    }
+
+    /**
+     * Creates a new {@link GeneratorAdapter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param mv the method visitor to which this adapter delegates calls.
+     * @param access the method's access flags (see {@link Opcodes}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     */
+    protected GeneratorAdapter(
+        final int api,
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc)
+    {
+        super(api, access, desc, mv);
+        this.access = access;
+        this.returnType = Type.getReturnType(desc);
+        this.argumentTypes = Type.getArgumentTypes(desc);
+    }
+
+    /**
+     * Creates a new {@link GeneratorAdapter}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #GeneratorAdapter(int, MethodVisitor, int, String, String)}
+     * version.
+     *
+     * @param access access flags of the adapted method.
+     * @param method the adapted method.
+     * @param mv the method visitor to which this adapter delegates calls.
+     */
+    public GeneratorAdapter(
+        final int access,
+        final Method method,
+        final MethodVisitor mv)
+    {
+        this(mv, access, null, method.getDescriptor());
+    }
+
+    /**
+     * Creates a new {@link GeneratorAdapter}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #GeneratorAdapter(int, MethodVisitor, int, String, String)}
+     * version.
+     *
+     * @param access access flags of the adapted method.
+     * @param method the adapted method.
+     * @param signature the signature of the adapted method (may be
+     *        <tt>null</tt>).
+     * @param exceptions the exceptions thrown by the adapted method (may be
+     *        <tt>null</tt>).
+     * @param cv the class visitor to which this adapter delegates calls.
+     */
+    public GeneratorAdapter(
+        final int access,
+        final Method method,
+        final String signature,
+        final Type[] exceptions,
+        final ClassVisitor cv)
+    {
+        this(access, method, cv.visitMethod(access,
+                method.getName(),
+                method.getDescriptor(),
+                signature,
+                getInternalNames(exceptions)));
+    }
+
+    /**
+     * Returns the internal names of the given types.
+     *
+     * @param types a set of types.
+     * @return the internal names of the given types.
+     */
+    private static String[] getInternalNames(final Type[] types) {
+        if (types == null) {
+            return null;
+        }
+        String[] names = new String[types.length];
+        for (int i = 0; i < names.length; ++i) {
+            names[i] = types[i].getInternalName();
+        }
+        return names;
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to push constants on the stack
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack.
+     */
+    public void push(final boolean value) {
+        push(value ? 1 : 0);
+    }
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack.
+     */
+    public void push(final int value) {
+        if (value >= -1 && value <= 5) {
+            mv.visitInsn(Opcodes.ICONST_0 + value);
+        } else if (value >= Byte.MIN_VALUE && value <= Byte.MAX_VALUE) {
+            mv.visitIntInsn(Opcodes.BIPUSH, value);
+        } else if (value >= Short.MIN_VALUE && value <= Short.MAX_VALUE) {
+            mv.visitIntInsn(Opcodes.SIPUSH, value);
+        } else {
+            mv.visitLdcInsn(new Integer(value));
+        }
+    }
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack.
+     */
+    public void push(final long value) {
+        if (value == 0L || value == 1L) {
+            mv.visitInsn(Opcodes.LCONST_0 + (int) value);
+        } else {
+            mv.visitLdcInsn(new Long(value));
+        }
+    }
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack.
+     */
+    public void push(final float value) {
+        int bits = Float.floatToIntBits(value);
+        if (bits == 0L || bits == 0x3f800000 || bits == 0x40000000) { // 0..2
+            mv.visitInsn(Opcodes.FCONST_0 + (int) value);
+        } else {
+            mv.visitLdcInsn(new Float(value));
+        }
+    }
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack.
+     */
+    public void push(final double value) {
+        long bits = Double.doubleToLongBits(value);
+        if (bits == 0L || bits == 0x3ff0000000000000L) { // +0.0d and 1.0d
+            mv.visitInsn(Opcodes.DCONST_0 + (int) value);
+        } else {
+            mv.visitLdcInsn(new Double(value));
+        }
+    }
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack. May be <tt>null</tt>.
+     */
+    public void push(final String value) {
+        if (value == null) {
+            mv.visitInsn(Opcodes.ACONST_NULL);
+        } else {
+            mv.visitLdcInsn(value);
+        }
+    }
+
+    /**
+     * Generates the instruction to push the given value on the stack.
+     *
+     * @param value the value to be pushed on the stack.
+     */
+    public void push(final Type value) {
+        if (value == null) {
+            mv.visitInsn(Opcodes.ACONST_NULL);
+        } else {
+            switch (value.getSort()) {
+                case Type.BOOLEAN:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Boolean",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.CHAR:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Character",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.BYTE:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Byte",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.SHORT:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Short",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.INT:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Integer",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.FLOAT:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Float",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.LONG:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Long",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                case Type.DOUBLE:
+                    mv.visitFieldInsn(Opcodes.GETSTATIC,
+                            "java/lang/Double",
+                            "TYPE",
+                            CLDESC);
+                    break;
+                default:
+                    mv.visitLdcInsn(value);
+            }
+        }
+    }
+
+    /**
+     * Generates the instruction to push a handle on the stack.
+     *
+     * @param handle the handle to be pushed on the stack.
+     */
+    public void push(final Handle handle) {
+        mv.visitLdcInsn(handle);
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to load and store method arguments
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the index of the given method argument in the frame's local
+     * variables array.
+     *
+     * @param arg the index of a method argument.
+     * @return the index of the given method argument in the frame's local
+     *         variables array.
+     */
+    private int getArgIndex(final int arg) {
+        int index = (access & Opcodes.ACC_STATIC) == 0 ? 1 : 0;
+        for (int i = 0; i < arg; i++) {
+            index += argumentTypes[i].getSize();
+        }
+        return index;
+    }
+
+    /**
+     * Generates the instruction to push a local variable on the stack.
+     *
+     * @param type the type of the local variable to be loaded.
+     * @param index an index in the frame's local variables array.
+     */
+    private void loadInsn(final Type type, final int index) {
+        mv.visitVarInsn(type.getOpcode(Opcodes.ILOAD), index);
+    }
+
+    /**
+     * Generates the instruction to store the top stack value in a local
+     * variable.
+     *
+     * @param type the type of the local variable to be stored.
+     * @param index an index in the frame's local variables array.
+     */
+    private void storeInsn(final Type type, final int index) {
+        mv.visitVarInsn(type.getOpcode(Opcodes.ISTORE), index);
+    }
+
+    /**
+     * Generates the instruction to load 'this' on the stack.
+     */
+    public void loadThis() {
+        if ((access & Opcodes.ACC_STATIC) != 0) {
+            throw new IllegalStateException("no 'this' pointer within static method");
+        }
+        mv.visitVarInsn(Opcodes.ALOAD, 0);
+    }
+
+    /**
+     * Generates the instruction to load the given method argument on the stack.
+     *
+     * @param arg the index of a method argument.
+     */
+    public void loadArg(final int arg) {
+        loadInsn(argumentTypes[arg], getArgIndex(arg));
+    }
+
+    /**
+     * Generates the instructions to load the given method arguments on the
+     * stack.
+     *
+     * @param arg the index of the first method argument to be loaded.
+     * @param count the number of method arguments to be loaded.
+     */
+    public void loadArgs(final int arg, final int count) {
+        int index = getArgIndex(arg);
+        for (int i = 0; i < count; ++i) {
+            Type t = argumentTypes[arg + i];
+            loadInsn(t, index);
+            index += t.getSize();
+        }
+    }
+
+    /**
+     * Generates the instructions to load all the method arguments on the stack.
+     */
+    public void loadArgs() {
+        loadArgs(0, argumentTypes.length);
+    }
+
+    /**
+     * Generates the instructions to load all the method arguments on the stack,
+     * as a single object array.
+     */
+    public void loadArgArray() {
+        push(argumentTypes.length);
+        newArray(OBJECT_TYPE);
+        for (int i = 0; i < argumentTypes.length; i++) {
+            dup();
+            push(i);
+            loadArg(i);
+            box(argumentTypes[i]);
+            arrayStore(OBJECT_TYPE);
+        }
+    }
+
+    /**
+     * Generates the instruction to store the top stack value in the given
+     * method argument.
+     *
+     * @param arg the index of a method argument.
+     */
+    public void storeArg(final int arg) {
+        storeInsn(argumentTypes[arg], getArgIndex(arg));
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to load and store local variables
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the type of the given local variable.
+     *
+     * @param local a local variable identifier, as returned by
+     *        {@link LocalVariablesSorter#newLocal(Type) newLocal()}.
+     * @return the type of the given local variable.
+     */
+    public Type getLocalType(final int local) {
+        return localTypes.get(local - firstLocal);
+    }
+
+    @Override
+    protected void setLocalType(final int local, final Type type) {
+        int index = local - firstLocal;
+        while (localTypes.size() < index + 1) {
+            localTypes.add(null);
+        }
+        localTypes.set(index, type);
+    }
+
+    /**
+     * Generates the instruction to load the given local variable on the stack.
+     *
+     * @param local a local variable identifier, as returned by
+     *        {@link LocalVariablesSorter#newLocal(Type) newLocal()}.
+     */
+    public void loadLocal(final int local) {
+        loadInsn(getLocalType(local), local);
+    }
+
+    /**
+     * Generates the instruction to load the given local variable on the stack.
+     *
+     * @param local a local variable identifier, as returned by
+     *        {@link LocalVariablesSorter#newLocal(Type) newLocal()}.
+     * @param type the type of this local variable.
+     */
+    public void loadLocal(final int local, final Type type) {
+        setLocalType(local, type);
+        loadInsn(type, local);
+    }
+
+    /**
+     * Generates the instruction to store the top stack value in the given local
+     * variable.
+     *
+     * @param local a local variable identifier, as returned by
+     *        {@link LocalVariablesSorter#newLocal(Type) newLocal()}.
+     */
+    public void storeLocal(final int local) {
+        storeInsn(getLocalType(local), local);
+    }
+
+    /**
+     * Generates the instruction to store the top stack value in the given local
+     * variable.
+     *
+     * @param local a local variable identifier, as returned by
+     *        {@link LocalVariablesSorter#newLocal(Type) newLocal()}.
+     * @param type the type of this local variable.
+     */
+    public void storeLocal(final int local, final Type type) {
+        setLocalType(local, type);
+        storeInsn(type, local);
+    }
+
+    /**
+     * Generates the instruction to load an element from an array.
+     *
+     * @param type the type of the array element to be loaded.
+     */
+    public void arrayLoad(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IALOAD));
+    }
+
+    /**
+     * Generates the instruction to store an element in an array.
+     *
+     * @param type the type of the array element to be stored.
+     */
+    public void arrayStore(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IASTORE));
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to manage the stack
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates a POP instruction.
+     */
+    public void pop() {
+        mv.visitInsn(Opcodes.POP);
+    }
+
+    /**
+     * Generates a POP2 instruction.
+     */
+    public void pop2() {
+        mv.visitInsn(Opcodes.POP2);
+    }
+
+    /**
+     * Generates a DUP instruction.
+     */
+    public void dup() {
+        mv.visitInsn(Opcodes.DUP);
+    }
+
+    /**
+     * Generates a DUP2 instruction.
+     */
+    public void dup2() {
+        mv.visitInsn(Opcodes.DUP2);
+    }
+
+    /**
+     * Generates a DUP_X1 instruction.
+     */
+    public void dupX1() {
+        mv.visitInsn(Opcodes.DUP_X1);
+    }
+
+    /**
+     * Generates a DUP_X2 instruction.
+     */
+    public void dupX2() {
+        mv.visitInsn(Opcodes.DUP_X2);
+    }
+
+    /**
+     * Generates a DUP2_X1 instruction.
+     */
+    public void dup2X1() {
+        mv.visitInsn(Opcodes.DUP2_X1);
+    }
+
+    /**
+     * Generates a DUP2_X2 instruction.
+     */
+    public void dup2X2() {
+        mv.visitInsn(Opcodes.DUP2_X2);
+    }
+
+    /**
+     * Generates a SWAP instruction.
+     */
+    public void swap() {
+        mv.visitInsn(Opcodes.SWAP);
+    }
+
+    /**
+     * Generates the instructions to swap the top two stack values.
+     *
+     * @param prev type of the top - 1 stack value.
+     * @param type type of the top stack value.
+     */
+    public void swap(final Type prev, final Type type) {
+        if (type.getSize() == 1) {
+            if (prev.getSize() == 1) {
+                swap(); // same as dupX1(), pop();
+            } else {
+                dupX2();
+                pop();
+            }
+        } else {
+            if (prev.getSize() == 1) {
+                dup2X1();
+                pop2();
+            } else {
+                dup2X2();
+                pop2();
+            }
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to do mathematical and logical operations
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates the instruction to do the specified mathematical or logical
+     * operation.
+     *
+     * @param op a mathematical or logical operation. Must be one of ADD, SUB,
+     *        MUL, DIV, REM, NEG, SHL, SHR, USHR, AND, OR, XOR.
+     * @param type the type of the operand(s) for this operation.
+     */
+    public void math(final int op, final Type type) {
+        mv.visitInsn(type.getOpcode(op));
+    }
+
+    /**
+     * Generates the instructions to compute the bitwise negation of the top
+     * stack value.
+     */
+    public void not() {
+        mv.visitInsn(Opcodes.ICONST_1);
+        mv.visitInsn(Opcodes.IXOR);
+    }
+
+    /**
+     * Generates the instruction to increment the given local variable.
+     *
+     * @param local the local variable to be incremented.
+     * @param amount the amount by which the local variable must be incremented.
+     */
+    public void iinc(final int local, final int amount) {
+        mv.visitIincInsn(local, amount);
+    }
+
+    /**
+     * Generates the instructions to cast a numerical value from one type to
+     * another.
+     *
+     * @param from the type of the top stack value
+     * @param to the type into which this value must be cast.
+     */
+    public void cast(final Type from, final Type to) {
+        if (from != to) {
+            if (from == Type.DOUBLE_TYPE) {
+                if (to == Type.FLOAT_TYPE) {
+                    mv.visitInsn(Opcodes.D2F);
+                } else if (to == Type.LONG_TYPE) {
+                    mv.visitInsn(Opcodes.D2L);
+                } else {
+                    mv.visitInsn(Opcodes.D2I);
+                    cast(Type.INT_TYPE, to);
+                }
+            } else if (from == Type.FLOAT_TYPE) {
+                if (to == Type.DOUBLE_TYPE) {
+                    mv.visitInsn(Opcodes.F2D);
+                } else if (to == Type.LONG_TYPE) {
+                    mv.visitInsn(Opcodes.F2L);
+                } else {
+                    mv.visitInsn(Opcodes.F2I);
+                    cast(Type.INT_TYPE, to);
+                }
+            } else if (from == Type.LONG_TYPE) {
+                if (to == Type.DOUBLE_TYPE) {
+                    mv.visitInsn(Opcodes.L2D);
+                } else if (to == Type.FLOAT_TYPE) {
+                    mv.visitInsn(Opcodes.L2F);
+                } else {
+                    mv.visitInsn(Opcodes.L2I);
+                    cast(Type.INT_TYPE, to);
+                }
+            } else {
+                if (to == Type.BYTE_TYPE) {
+                    mv.visitInsn(Opcodes.I2B);
+                } else if (to == Type.CHAR_TYPE) {
+                    mv.visitInsn(Opcodes.I2C);
+                } else if (to == Type.DOUBLE_TYPE) {
+                    mv.visitInsn(Opcodes.I2D);
+                } else if (to == Type.FLOAT_TYPE) {
+                    mv.visitInsn(Opcodes.I2F);
+                } else if (to == Type.LONG_TYPE) {
+                    mv.visitInsn(Opcodes.I2L);
+                } else if (to == Type.SHORT_TYPE) {
+                    mv.visitInsn(Opcodes.I2S);
+                }
+            }
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to do boxing and unboxing operations
+    // ------------------------------------------------------------------------
+
+    private static Type getBoxedType(final Type type) {
+        switch (type.getSort()) {
+            case Type.BYTE:
+                return BYTE_TYPE;
+            case Type.BOOLEAN:
+                return BOOLEAN_TYPE;
+            case Type.SHORT:
+                return SHORT_TYPE;
+            case Type.CHAR:
+                return CHARACTER_TYPE;
+            case Type.INT:
+                return INTEGER_TYPE;
+            case Type.FLOAT:
+                return FLOAT_TYPE;
+            case Type.LONG:
+                return LONG_TYPE;
+            case Type.DOUBLE:
+                return DOUBLE_TYPE;
+        }
+        return type;
+    }
+
+    /**
+     * Generates the instructions to box the top stack value. This value is
+     * replaced by its boxed equivalent on top of the stack.
+     *
+     * @param type the type of the top stack value.
+     */
+    public void box(final Type type) {
+        if (type.getSort() == Type.OBJECT || type.getSort() == Type.ARRAY) {
+            return;
+        }
+        if (type == Type.VOID_TYPE) {
+            push((String) null);
+        } else {
+            Type boxed = getBoxedType(type);
+            newInstance(boxed);
+            if (type.getSize() == 2) {
+                // Pp -> Ppo -> oPpo -> ooPpo -> ooPp -> o
+                dupX2();
+                dupX2();
+                pop();
+            } else {
+                // p -> po -> opo -> oop -> o
+                dupX1();
+                swap();
+            }
+            invokeConstructor(boxed, new Method("<init>",
+                    Type.VOID_TYPE,
+                    new Type[] { type }));
+        }
+    }
+
+    /**
+     * Generates the instructions to box the top stack value using Java 5's
+     * valueOf() method. This value is replaced by its boxed equivalent on top
+     * of the stack.
+     *
+     * @param type the type of the top stack value.
+     */
+    public void valueOf(final Type type) {
+        if (type.getSort() == Type.OBJECT || type.getSort() == Type.ARRAY) {
+            return;
+        }
+        if (type == Type.VOID_TYPE) {
+            push((String) null);
+        } else {
+            Type boxed = getBoxedType(type);
+            invokeStatic(boxed, new Method("valueOf",
+                    boxed,
+                    new Type[] { type }));
+        }
+    }
+
+    /**
+     * Generates the instructions to unbox the top stack value. This value is
+     * replaced by its unboxed equivalent on top of the stack.
+     *
+     * @param type the type of the top stack value.
+     */
+    public void unbox(final Type type) {
+        Type t = NUMBER_TYPE;
+        Method sig = null;
+        switch (type.getSort()) {
+            case Type.VOID:
+                return;
+            case Type.CHAR:
+                t = CHARACTER_TYPE;
+                sig = CHAR_VALUE;
+                break;
+            case Type.BOOLEAN:
+                t = BOOLEAN_TYPE;
+                sig = BOOLEAN_VALUE;
+                break;
+            case Type.DOUBLE:
+                sig = DOUBLE_VALUE;
+                break;
+            case Type.FLOAT:
+                sig = FLOAT_VALUE;
+                break;
+            case Type.LONG:
+                sig = LONG_VALUE;
+                break;
+            case Type.INT:
+            case Type.SHORT:
+            case Type.BYTE:
+                sig = INT_VALUE;
+        }
+        if (sig == null) {
+            checkCast(type);
+        } else {
+            checkCast(t);
+            invokeVirtual(t, sig);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to jump to other instructions
+    // ------------------------------------------------------------------------
+
+    /**
+     * Creates a new {@link Label}.
+     *
+     * @return a new {@link Label}.
+     */
+    public Label newLabel() {
+        return new Label();
+    }
+
+    /**
+     * Marks the current code position with the given label.
+     *
+     * @param label a label.
+     */
+    public void mark(final Label label) {
+        mv.visitLabel(label);
+    }
+
+    /**
+     * Marks the current code position with a new label.
+     *
+     * @return the label that was created to mark the current code position.
+     */
+    public Label mark() {
+        Label label = new Label();
+        mv.visitLabel(label);
+        return label;
+    }
+
+    /**
+     * Generates the instructions to jump to a label based on the comparison of
+     * the top two stack values.
+     *
+     * @param type the type of the top two stack values.
+     * @param mode how these values must be compared. One of EQ, NE, LT, GE, GT,
+     *        LE.
+     * @param label where to jump if the comparison result is <tt>true</tt>.
+     */
+    public void ifCmp(final Type type, final int mode, final Label label) {
+        switch (type.getSort()) {
+            case Type.LONG:
+                mv.visitInsn(Opcodes.LCMP);
+                break;
+            case Type.DOUBLE:
+                mv.visitInsn(mode == GE || mode == GT ? Opcodes.DCMPG : Opcodes.DCMPL);
+                break;
+            case Type.FLOAT:
+                mv.visitInsn(mode == GE || mode == GT ? Opcodes.FCMPG : Opcodes.FCMPL);
+                break;
+            case Type.ARRAY:
+            case Type.OBJECT:
+                switch (mode) {
+                    case EQ:
+                        mv.visitJumpInsn(Opcodes.IF_ACMPEQ, label);
+                        return;
+                    case NE:
+                        mv.visitJumpInsn(Opcodes.IF_ACMPNE, label);
+                        return;
+                }
+                throw new IllegalArgumentException("Bad comparison for type "
+                        + type);
+            default:
+                int intOp = -1;
+                switch (mode) {
+                    case EQ:
+                        intOp = Opcodes.IF_ICMPEQ;
+                        break;
+                    case NE:
+                        intOp = Opcodes.IF_ICMPNE;
+                        break;
+                    case GE:
+                        intOp = Opcodes.IF_ICMPGE;
+                        break;
+                    case LT:
+                        intOp = Opcodes.IF_ICMPLT;
+                        break;
+                    case LE:
+                        intOp = Opcodes.IF_ICMPLE;
+                        break;
+                    case GT:
+                        intOp = Opcodes.IF_ICMPGT;
+                        break;
+                }
+                mv.visitJumpInsn(intOp, label);
+                return;
+        }
+        mv.visitJumpInsn(mode, label);
+    }
+
+    /**
+     * Generates the instructions to jump to a label based on the comparison of
+     * the top two integer stack values.
+     *
+     * @param mode how these values must be compared. One of EQ, NE, LT, GE, GT,
+     *        LE.
+     * @param label where to jump if the comparison result is <tt>true</tt>.
+     */
+    public void ifICmp(final int mode, final Label label) {
+        ifCmp(Type.INT_TYPE, mode, label);
+    }
+
+    /**
+     * Generates the instructions to jump to a label based on the comparison of
+     * the top integer stack value with zero.
+     *
+     * @param mode how these values must be compared. One of EQ, NE, LT, GE, GT,
+     *        LE.
+     * @param label where to jump if the comparison result is <tt>true</tt>.
+     */
+    public void ifZCmp(final int mode, final Label label) {
+        mv.visitJumpInsn(mode, label);
+    }
+
+    /**
+     * Generates the instruction to jump to the given label if the top stack
+     * value is null.
+     *
+     * @param label where to jump if the condition is <tt>true</tt>.
+     */
+    public void ifNull(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFNULL, label);
+    }
+
+    /**
+     * Generates the instruction to jump to the given label if the top stack
+     * value is not null.
+     *
+     * @param label where to jump if the condition is <tt>true</tt>.
+     */
+    public void ifNonNull(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFNONNULL, label);
+    }
+
+    /**
+     * Generates the instruction to jump to the given label.
+     *
+     * @param label where to jump if the condition is <tt>true</tt>.
+     */
+    public void goTo(final Label label) {
+        mv.visitJumpInsn(Opcodes.GOTO, label);
+    }
+
+    /**
+     * Generates a RET instruction.
+     *
+     * @param local a local variable identifier, as returned by
+     *        {@link LocalVariablesSorter#newLocal(Type) newLocal()}.
+     */
+    public void ret(final int local) {
+        mv.visitVarInsn(Opcodes.RET, local);
+    }
+
+    /**
+     * Generates the instructions for a switch statement.
+     *
+     * @param keys the switch case keys.
+     * @param generator a generator to generate the code for the switch cases.
+     */
+    public void tableSwitch(
+        final int[] keys,
+        final TableSwitchGenerator generator)
+    {
+        float density;
+        if (keys.length == 0) {
+            density = 0;
+        } else {
+            density = (float) keys.length
+                    / (keys[keys.length - 1] - keys[0] + 1);
+        }
+        tableSwitch(keys, generator, density >= 0.5f);
+    }
+
+    /**
+     * Generates the instructions for a switch statement.
+     *
+     * @param keys the switch case keys.
+     * @param generator a generator to generate the code for the switch cases.
+     * @param useTable <tt>true</tt> to use a TABLESWITCH instruction, or
+     *        <tt>false</tt> to use a LOOKUPSWITCH instruction.
+     */
+    public void tableSwitch(
+        final int[] keys,
+        final TableSwitchGenerator generator,
+        final boolean useTable)
+    {
+        for (int i = 1; i < keys.length; ++i) {
+            if (keys[i] < keys[i - 1]) {
+                throw new IllegalArgumentException("keys must be sorted ascending");
+            }
+        }
+        Label def = newLabel();
+        Label end = newLabel();
+        if (keys.length > 0) {
+            int len = keys.length;
+            int min = keys[0];
+            int max = keys[len - 1];
+            int range = max - min + 1;
+            if (useTable) {
+                Label[] labels = new Label[range];
+                Arrays.fill(labels, def);
+                for (int i = 0; i < len; ++i) {
+                    labels[keys[i] - min] = newLabel();
+                }
+                mv.visitTableSwitchInsn(min, max, def, labels);
+                for (int i = 0; i < range; ++i) {
+                    Label label = labels[i];
+                    if (label != def) {
+                        mark(label);
+                        generator.generateCase(i + min, end);
+                    }
+                }
+            } else {
+                Label[] labels = new Label[len];
+                for (int i = 0; i < len; ++i) {
+                    labels[i] = newLabel();
+                }
+                mv.visitLookupSwitchInsn(def, keys, labels);
+                for (int i = 0; i < len; ++i) {
+                    mark(labels[i]);
+                    generator.generateCase(keys[i], end);
+                }
+            }
+        }
+        mark(def);
+        generator.generateDefault();
+        mark(end);
+    }
+
+    /**
+     * Generates the instruction to return the top stack value to the caller.
+     */
+    public void returnValue() {
+        mv.visitInsn(returnType.getOpcode(Opcodes.IRETURN));
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to load and store fields
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates a get field or set field instruction.
+     *
+     * @param opcode the instruction's opcode.
+     * @param ownerType the class in which the field is defined.
+     * @param name the name of the field.
+     * @param fieldType the type of the field.
+     */
+    private void fieldInsn(
+        final int opcode,
+        final Type ownerType,
+        final String name,
+        final Type fieldType)
+    {
+        mv.visitFieldInsn(opcode,
+                ownerType.getInternalName(),
+                name,
+                fieldType.getDescriptor());
+    }
+
+    /**
+     * Generates the instruction to push the value of a static field on the
+     * stack.
+     *
+     * @param owner the class in which the field is defined.
+     * @param name the name of the field.
+     * @param type the type of the field.
+     */
+    public void getStatic(final Type owner, final String name, final Type type)
+    {
+        fieldInsn(Opcodes.GETSTATIC, owner, name, type);
+    }
+
+    /**
+     * Generates the instruction to store the top stack value in a static field.
+     *
+     * @param owner the class in which the field is defined.
+     * @param name the name of the field.
+     * @param type the type of the field.
+     */
+    public void putStatic(final Type owner, final String name, final Type type)
+    {
+        fieldInsn(Opcodes.PUTSTATIC, owner, name, type);
+    }
+
+    /**
+     * Generates the instruction to push the value of a non static field on the
+     * stack.
+     *
+     * @param owner the class in which the field is defined.
+     * @param name the name of the field.
+     * @param type the type of the field.
+     */
+    public void getField(final Type owner, final String name, final Type type) {
+        fieldInsn(Opcodes.GETFIELD, owner, name, type);
+    }
+
+    /**
+     * Generates the instruction to store the top stack value in a non static
+     * field.
+     *
+     * @param owner the class in which the field is defined.
+     * @param name the name of the field.
+     * @param type the type of the field.
+     */
+    public void putField(final Type owner, final String name, final Type type) {
+        fieldInsn(Opcodes.PUTFIELD, owner, name, type);
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to invoke methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates an invoke method instruction.
+     *
+     * @param opcode the instruction's opcode.
+     * @param type the class in which the method is defined.
+     * @param method the method to be invoked.
+     */
+    private void invokeInsn(
+        final int opcode,
+        final Type type,
+        final Method method)
+    {
+        String owner = type.getSort() == Type.ARRAY
+                ? type.getDescriptor()
+                : type.getInternalName();
+        mv.visitMethodInsn(opcode,
+                owner,
+                method.getName(),
+                method.getDescriptor());
+    }
+
+    /**
+     * Generates the instruction to invoke a normal method.
+     *
+     * @param owner the class in which the method is defined.
+     * @param method the method to be invoked.
+     */
+    public void invokeVirtual(final Type owner, final Method method) {
+        invokeInsn(Opcodes.INVOKEVIRTUAL, owner, method);
+    }
+
+    /**
+     * Generates the instruction to invoke a constructor.
+     *
+     * @param type the class in which the constructor is defined.
+     * @param method the constructor to be invoked.
+     */
+    public void invokeConstructor(final Type type, final Method method) {
+        invokeInsn(Opcodes.INVOKESPECIAL, type, method);
+    }
+
+    /**
+     * Generates the instruction to invoke a static method.
+     *
+     * @param owner the class in which the method is defined.
+     * @param method the method to be invoked.
+     */
+    public void invokeStatic(final Type owner, final Method method) {
+        invokeInsn(Opcodes.INVOKESTATIC, owner, method);
+    }
+
+    /**
+     * Generates the instruction to invoke an interface method.
+     *
+     * @param owner the class in which the method is defined.
+     * @param method the method to be invoked.
+     */
+    public void invokeInterface(final Type owner, final Method method) {
+        invokeInsn(Opcodes.INVOKEINTERFACE, owner, method);
+    }
+
+    /**
+     * Generates an invokedynamic instruction.
+     *
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param bsm the bootstrap method.
+     * @param bsmArgs the bootstrap method constant arguments. Each argument
+     *        must be an {@link Integer}, {@link Float}, {@link Long},
+     *        {@link Double}, {@link String}, {@link Type} or {@link Handle}
+     *        value. This method is allowed to modify the content of the array
+     *        so a caller should expect that this array may change.
+     */
+    public void invokeDynamic(String name, String desc, Handle bsm, Object... bsmArgs) {
+        mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+    }
+
+    // ------------------------------------------------------------------------
+    // Instructions to create objects and arrays
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates a type dependent instruction.
+     *
+     * @param opcode the instruction's opcode.
+     * @param type the instruction's operand.
+     */
+    private void typeInsn(final int opcode, final Type type) {
+        mv.visitTypeInsn(opcode, type.getInternalName());
+    }
+
+    /**
+     * Generates the instruction to create a new object.
+     *
+     * @param type the class of the object to be created.
+     */
+    public void newInstance(final Type type) {
+        typeInsn(Opcodes.NEW, type);
+    }
+
+    /**
+     * Generates the instruction to create a new array.
+     *
+     * @param type the type of the array elements.
+     */
+    public void newArray(final Type type) {
+        int typ;
+        switch (type.getSort()) {
+            case Type.BOOLEAN:
+                typ = Opcodes.T_BOOLEAN;
+                break;
+            case Type.CHAR:
+                typ = Opcodes.T_CHAR;
+                break;
+            case Type.BYTE:
+                typ = Opcodes.T_BYTE;
+                break;
+            case Type.SHORT:
+                typ = Opcodes.T_SHORT;
+                break;
+            case Type.INT:
+                typ = Opcodes.T_INT;
+                break;
+            case Type.FLOAT:
+                typ = Opcodes.T_FLOAT;
+                break;
+            case Type.LONG:
+                typ = Opcodes.T_LONG;
+                break;
+            case Type.DOUBLE:
+                typ = Opcodes.T_DOUBLE;
+                break;
+            default:
+                typeInsn(Opcodes.ANEWARRAY, type);
+                return;
+        }
+        mv.visitIntInsn(Opcodes.NEWARRAY, typ);
+    }
+
+    // ------------------------------------------------------------------------
+    // Miscelaneous instructions
+    // ------------------------------------------------------------------------
+
+    /**
+     * Generates the instruction to compute the length of an array.
+     */
+    public void arrayLength() {
+        mv.visitInsn(Opcodes.ARRAYLENGTH);
+    }
+
+    /**
+     * Generates the instruction to throw an exception.
+     */
+    public void throwException() {
+        mv.visitInsn(Opcodes.ATHROW);
+    }
+
+    /**
+     * Generates the instructions to create and throw an exception. The
+     * exception class must have a constructor with a single String argument.
+     *
+     * @param type the class of the exception to be thrown.
+     * @param msg the detailed message of the exception.
+     */
+    public void throwException(final Type type, final String msg) {
+        newInstance(type);
+        dup();
+        push(msg);
+        invokeConstructor(type, Method.getMethod("void <init> (String)"));
+        throwException();
+    }
+
+    /**
+     * Generates the instruction to check that the top stack value is of the
+     * given type.
+     *
+     * @param type a class or interface type.
+     */
+    public void checkCast(final Type type) {
+        if (!type.equals(OBJECT_TYPE)) {
+            typeInsn(Opcodes.CHECKCAST, type);
+        }
+    }
+
+    /**
+     * Generates the instruction to test if the top stack value is of the given
+     * type.
+     *
+     * @param type a class or interface type.
+     */
+    public void instanceOf(final Type type) {
+        typeInsn(Opcodes.INSTANCEOF, type);
+    }
+
+    /**
+     * Generates the instruction to get the monitor of the top stack value.
+     */
+    public void monitorEnter() {
+        mv.visitInsn(Opcodes.MONITORENTER);
+    }
+
+    /**
+     * Generates the instruction to release the monitor of the top stack value.
+     */
+    public void monitorExit() {
+        mv.visitInsn(Opcodes.MONITOREXIT);
+    }
+
+    // ------------------------------------------------------------------------
+    // Non instructions
+    // ------------------------------------------------------------------------
+
+    /**
+     * Marks the end of the visited method.
+     */
+    public void endMethod() {
+        if ((access & Opcodes.ACC_ABSTRACT) == 0) {
+            mv.visitMaxs(0, 0);
+        }
+        mv.visitEnd();
+    }
+
+    /**
+     * Marks the start of an exception handler.
+     *
+     * @param start beginning of the exception handler's scope (inclusive).
+     * @param end end of the exception handler's scope (exclusive).
+     * @param exception internal name of the type of exceptions handled by the
+     *        handler.
+     */
+    public void catchException(
+        final Label start,
+        final Label end,
+        final Type exception)
+    {
+        if (exception == null) {
+            mv.visitTryCatchBlock(start, end, mark(), null);
+        } else {
+            mv.visitTryCatchBlock(start, end, mark(), exception.getInternalName());
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/InstructionAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1170 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link MethodVisitor} providing a more detailed API to generate and
+ * transform instructions.
+ *
+ * @author Eric Bruneton
+ */
+public class InstructionAdapter extends MethodVisitor {
+
+    public final static Type OBJECT_TYPE = Type.getType("Ljava/lang/Object;");
+
+    /**
+     * Creates a new {@link InstructionAdapter}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #InstructionAdapter(int, MethodVisitor)} version.
+     *
+     * @param mv the method visitor to which this adapter delegates calls.
+     */
+    public InstructionAdapter(final MethodVisitor mv) {
+        this(Opcodes.ASM4, mv);
+    }
+
+    /**
+     * Creates a new {@link InstructionAdapter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param mv the method visitor to which this adapter delegates calls.
+     */
+    protected InstructionAdapter(final int api, final MethodVisitor mv) {
+        super(api, mv);
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        switch (opcode) {
+            case Opcodes.NOP:
+                nop();
+                break;
+            case Opcodes.ACONST_NULL:
+                aconst(null);
+                break;
+            case Opcodes.ICONST_M1:
+            case Opcodes.ICONST_0:
+            case Opcodes.ICONST_1:
+            case Opcodes.ICONST_2:
+            case Opcodes.ICONST_3:
+            case Opcodes.ICONST_4:
+            case Opcodes.ICONST_5:
+                iconst(opcode - Opcodes.ICONST_0);
+                break;
+            case Opcodes.LCONST_0:
+            case Opcodes.LCONST_1:
+                lconst(opcode - Opcodes.LCONST_0);
+                break;
+            case Opcodes.FCONST_0:
+            case Opcodes.FCONST_1:
+            case Opcodes.FCONST_2:
+                fconst(opcode - Opcodes.FCONST_0);
+                break;
+            case Opcodes.DCONST_0:
+            case Opcodes.DCONST_1:
+                dconst(opcode - Opcodes.DCONST_0);
+                break;
+            case Opcodes.IALOAD:
+                aload(Type.INT_TYPE);
+                break;
+            case Opcodes.LALOAD:
+                aload(Type.LONG_TYPE);
+                break;
+            case Opcodes.FALOAD:
+                aload(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DALOAD:
+                aload(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.AALOAD:
+                aload(OBJECT_TYPE);
+                break;
+            case Opcodes.BALOAD:
+                aload(Type.BYTE_TYPE);
+                break;
+            case Opcodes.CALOAD:
+                aload(Type.CHAR_TYPE);
+                break;
+            case Opcodes.SALOAD:
+                aload(Type.SHORT_TYPE);
+                break;
+            case Opcodes.IASTORE:
+                astore(Type.INT_TYPE);
+                break;
+            case Opcodes.LASTORE:
+                astore(Type.LONG_TYPE);
+                break;
+            case Opcodes.FASTORE:
+                astore(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DASTORE:
+                astore(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.AASTORE:
+                astore(OBJECT_TYPE);
+                break;
+            case Opcodes.BASTORE:
+                astore(Type.BYTE_TYPE);
+                break;
+            case Opcodes.CASTORE:
+                astore(Type.CHAR_TYPE);
+                break;
+            case Opcodes.SASTORE:
+                astore(Type.SHORT_TYPE);
+                break;
+            case Opcodes.POP:
+                pop();
+                break;
+            case Opcodes.POP2:
+                pop2();
+                break;
+            case Opcodes.DUP:
+                dup();
+                break;
+            case Opcodes.DUP_X1:
+                dupX1();
+                break;
+            case Opcodes.DUP_X2:
+                dupX2();
+                break;
+            case Opcodes.DUP2:
+                dup2();
+                break;
+            case Opcodes.DUP2_X1:
+                dup2X1();
+                break;
+            case Opcodes.DUP2_X2:
+                dup2X2();
+                break;
+            case Opcodes.SWAP:
+                swap();
+                break;
+            case Opcodes.IADD:
+                add(Type.INT_TYPE);
+                break;
+            case Opcodes.LADD:
+                add(Type.LONG_TYPE);
+                break;
+            case Opcodes.FADD:
+                add(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DADD:
+                add(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.ISUB:
+                sub(Type.INT_TYPE);
+                break;
+            case Opcodes.LSUB:
+                sub(Type.LONG_TYPE);
+                break;
+            case Opcodes.FSUB:
+                sub(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DSUB:
+                sub(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.IMUL:
+                mul(Type.INT_TYPE);
+                break;
+            case Opcodes.LMUL:
+                mul(Type.LONG_TYPE);
+                break;
+            case Opcodes.FMUL:
+                mul(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DMUL:
+                mul(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.IDIV:
+                div(Type.INT_TYPE);
+                break;
+            case Opcodes.LDIV:
+                div(Type.LONG_TYPE);
+                break;
+            case Opcodes.FDIV:
+                div(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DDIV:
+                div(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.IREM:
+                rem(Type.INT_TYPE);
+                break;
+            case Opcodes.LREM:
+                rem(Type.LONG_TYPE);
+                break;
+            case Opcodes.FREM:
+                rem(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DREM:
+                rem(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.INEG:
+                neg(Type.INT_TYPE);
+                break;
+            case Opcodes.LNEG:
+                neg(Type.LONG_TYPE);
+                break;
+            case Opcodes.FNEG:
+                neg(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DNEG:
+                neg(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.ISHL:
+                shl(Type.INT_TYPE);
+                break;
+            case Opcodes.LSHL:
+                shl(Type.LONG_TYPE);
+                break;
+            case Opcodes.ISHR:
+                shr(Type.INT_TYPE);
+                break;
+            case Opcodes.LSHR:
+                shr(Type.LONG_TYPE);
+                break;
+            case Opcodes.IUSHR:
+                ushr(Type.INT_TYPE);
+                break;
+            case Opcodes.LUSHR:
+                ushr(Type.LONG_TYPE);
+                break;
+            case Opcodes.IAND:
+                and(Type.INT_TYPE);
+                break;
+            case Opcodes.LAND:
+                and(Type.LONG_TYPE);
+                break;
+            case Opcodes.IOR:
+                or(Type.INT_TYPE);
+                break;
+            case Opcodes.LOR:
+                or(Type.LONG_TYPE);
+                break;
+            case Opcodes.IXOR:
+                xor(Type.INT_TYPE);
+                break;
+            case Opcodes.LXOR:
+                xor(Type.LONG_TYPE);
+                break;
+            case Opcodes.I2L:
+                cast(Type.INT_TYPE, Type.LONG_TYPE);
+                break;
+            case Opcodes.I2F:
+                cast(Type.INT_TYPE, Type.FLOAT_TYPE);
+                break;
+            case Opcodes.I2D:
+                cast(Type.INT_TYPE, Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.L2I:
+                cast(Type.LONG_TYPE, Type.INT_TYPE);
+                break;
+            case Opcodes.L2F:
+                cast(Type.LONG_TYPE, Type.FLOAT_TYPE);
+                break;
+            case Opcodes.L2D:
+                cast(Type.LONG_TYPE, Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.F2I:
+                cast(Type.FLOAT_TYPE, Type.INT_TYPE);
+                break;
+            case Opcodes.F2L:
+                cast(Type.FLOAT_TYPE, Type.LONG_TYPE);
+                break;
+            case Opcodes.F2D:
+                cast(Type.FLOAT_TYPE, Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.D2I:
+                cast(Type.DOUBLE_TYPE, Type.INT_TYPE);
+                break;
+            case Opcodes.D2L:
+                cast(Type.DOUBLE_TYPE, Type.LONG_TYPE);
+                break;
+            case Opcodes.D2F:
+                cast(Type.DOUBLE_TYPE, Type.FLOAT_TYPE);
+                break;
+            case Opcodes.I2B:
+                cast(Type.INT_TYPE, Type.BYTE_TYPE);
+                break;
+            case Opcodes.I2C:
+                cast(Type.INT_TYPE, Type.CHAR_TYPE);
+                break;
+            case Opcodes.I2S:
+                cast(Type.INT_TYPE, Type.SHORT_TYPE);
+                break;
+            case Opcodes.LCMP:
+                lcmp();
+                break;
+            case Opcodes.FCMPL:
+                cmpl(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.FCMPG:
+                cmpg(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DCMPL:
+                cmpl(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.DCMPG:
+                cmpg(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.IRETURN:
+                areturn(Type.INT_TYPE);
+                break;
+            case Opcodes.LRETURN:
+                areturn(Type.LONG_TYPE);
+                break;
+            case Opcodes.FRETURN:
+                areturn(Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DRETURN:
+                areturn(Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.ARETURN:
+                areturn(OBJECT_TYPE);
+                break;
+            case Opcodes.RETURN:
+                areturn(Type.VOID_TYPE);
+                break;
+            case Opcodes.ARRAYLENGTH:
+                arraylength();
+                break;
+            case Opcodes.ATHROW:
+                athrow();
+                break;
+            case Opcodes.MONITORENTER:
+                monitorenter();
+                break;
+            case Opcodes.MONITOREXIT:
+                monitorexit();
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        switch (opcode) {
+            case Opcodes.BIPUSH:
+                iconst(operand);
+                break;
+            case Opcodes.SIPUSH:
+                iconst(operand);
+                break;
+            case Opcodes.NEWARRAY:
+                switch (operand) {
+                    case Opcodes.T_BOOLEAN:
+                        newarray(Type.BOOLEAN_TYPE);
+                        break;
+                    case Opcodes.T_CHAR:
+                        newarray(Type.CHAR_TYPE);
+                        break;
+                    case Opcodes.T_BYTE:
+                        newarray(Type.BYTE_TYPE);
+                        break;
+                    case Opcodes.T_SHORT:
+                        newarray(Type.SHORT_TYPE);
+                        break;
+                    case Opcodes.T_INT:
+                        newarray(Type.INT_TYPE);
+                        break;
+                    case Opcodes.T_FLOAT:
+                        newarray(Type.FLOAT_TYPE);
+                        break;
+                    case Opcodes.T_LONG:
+                        newarray(Type.LONG_TYPE);
+                        break;
+                    case Opcodes.T_DOUBLE:
+                        newarray(Type.DOUBLE_TYPE);
+                        break;
+                    default:
+                        throw new IllegalArgumentException();
+                }
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        switch (opcode) {
+            case Opcodes.ILOAD:
+                load(var, Type.INT_TYPE);
+                break;
+            case Opcodes.LLOAD:
+                load(var, Type.LONG_TYPE);
+                break;
+            case Opcodes.FLOAD:
+                load(var, Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DLOAD:
+                load(var, Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.ALOAD:
+                load(var, OBJECT_TYPE);
+                break;
+            case Opcodes.ISTORE:
+                store(var, Type.INT_TYPE);
+                break;
+            case Opcodes.LSTORE:
+                store(var, Type.LONG_TYPE);
+                break;
+            case Opcodes.FSTORE:
+                store(var, Type.FLOAT_TYPE);
+                break;
+            case Opcodes.DSTORE:
+                store(var, Type.DOUBLE_TYPE);
+                break;
+            case Opcodes.ASTORE:
+                store(var, OBJECT_TYPE);
+                break;
+            case Opcodes.RET:
+                ret(var);
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        Type t = Type.getObjectType(type);
+        switch (opcode) {
+            case Opcodes.NEW:
+                anew(t);
+                break;
+            case Opcodes.ANEWARRAY:
+                newarray(t);
+                break;
+            case Opcodes.CHECKCAST:
+                checkcast(t);
+                break;
+            case Opcodes.INSTANCEOF:
+                instanceOf(t);
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        switch (opcode) {
+            case Opcodes.GETSTATIC:
+                getstatic(owner, name, desc);
+                break;
+            case Opcodes.PUTSTATIC:
+                putstatic(owner, name, desc);
+                break;
+            case Opcodes.GETFIELD:
+                getfield(owner, name, desc);
+                break;
+            case Opcodes.PUTFIELD:
+                putfield(owner, name, desc);
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        switch (opcode) {
+            case Opcodes.INVOKESPECIAL:
+                invokespecial(owner, name, desc);
+                break;
+            case Opcodes.INVOKEVIRTUAL:
+                invokevirtual(owner, name, desc);
+                break;
+            case Opcodes.INVOKESTATIC:
+                invokestatic(owner, name, desc);
+                break;
+            case Opcodes.INVOKEINTERFACE:
+                invokeinterface(owner, name, desc);
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+       invokedynamic(name, desc, bsm, bsmArgs);
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        switch (opcode) {
+            case Opcodes.IFEQ:
+                ifeq(label);
+                break;
+            case Opcodes.IFNE:
+                ifne(label);
+                break;
+            case Opcodes.IFLT:
+                iflt(label);
+                break;
+            case Opcodes.IFGE:
+                ifge(label);
+                break;
+            case Opcodes.IFGT:
+                ifgt(label);
+                break;
+            case Opcodes.IFLE:
+                ifle(label);
+                break;
+            case Opcodes.IF_ICMPEQ:
+                ificmpeq(label);
+                break;
+            case Opcodes.IF_ICMPNE:
+                ificmpne(label);
+                break;
+            case Opcodes.IF_ICMPLT:
+                ificmplt(label);
+                break;
+            case Opcodes.IF_ICMPGE:
+                ificmpge(label);
+                break;
+            case Opcodes.IF_ICMPGT:
+                ificmpgt(label);
+                break;
+            case Opcodes.IF_ICMPLE:
+                ificmple(label);
+                break;
+            case Opcodes.IF_ACMPEQ:
+                ifacmpeq(label);
+                break;
+            case Opcodes.IF_ACMPNE:
+                ifacmpne(label);
+                break;
+            case Opcodes.GOTO:
+                goTo(label);
+                break;
+            case Opcodes.JSR:
+                jsr(label);
+                break;
+            case Opcodes.IFNULL:
+                ifnull(label);
+                break;
+            case Opcodes.IFNONNULL:
+                ifnonnull(label);
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        mark(label);
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        if (cst instanceof Integer) {
+            int val = ((Integer) cst).intValue();
+            iconst(val);
+        } else if (cst instanceof Byte) {
+            int val = ((Byte) cst).intValue();
+            iconst(val);
+        } else if (cst instanceof Character) {
+            int val = ((Character) cst).charValue();
+            iconst(val);
+        } else if (cst instanceof Short) {
+            int val = ((Short) cst).intValue();
+            iconst(val);
+        } else if (cst instanceof Boolean) {
+            int val = ((Boolean) cst).booleanValue() ? 1 : 0;
+            iconst(val);
+        } else if (cst instanceof Float) {
+            float val = ((Float) cst).floatValue();
+            fconst(val);
+        } else if (cst instanceof Long) {
+            long val = ((Long) cst).longValue();
+            lconst(val);
+        } else if (cst instanceof Double) {
+            double val = ((Double) cst).doubleValue();
+            dconst(val);
+        } else if (cst instanceof String) {
+            aconst(cst);
+        } else if (cst instanceof Type) {
+            tconst((Type) cst);
+        } else if (cst instanceof Handle) {
+            hconst((Handle) cst);
+        } else {
+            throw new IllegalArgumentException();
+        }
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        iinc(var, increment);
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        tableswitch(min, max, dflt, labels);
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        lookupswitch(dflt, keys, labels);
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        multianewarray(desc, dims);
+    }
+
+    // -----------------------------------------------------------------------
+
+    public void nop() {
+        mv.visitInsn(Opcodes.NOP);
+    }
+
+    public void aconst(final Object cst) {
+        if (cst == null) {
+            mv.visitInsn(Opcodes.ACONST_NULL);
+        } else {
+            mv.visitLdcInsn(cst);
+        }
+    }
+
+    public void iconst(final int cst) {
+        if (cst >= -1 && cst <= 5) {
+            mv.visitInsn(Opcodes.ICONST_0 + cst);
+        } else if (cst >= Byte.MIN_VALUE && cst <= Byte.MAX_VALUE) {
+            mv.visitIntInsn(Opcodes.BIPUSH, cst);
+        } else if (cst >= Short.MIN_VALUE && cst <= Short.MAX_VALUE) {
+            mv.visitIntInsn(Opcodes.SIPUSH, cst);
+        } else {
+            mv.visitLdcInsn(new Integer(cst));
+        }
+    }
+
+    public void lconst(final long cst) {
+        if (cst == 0L || cst == 1L) {
+            mv.visitInsn(Opcodes.LCONST_0 + (int) cst);
+        } else {
+            mv.visitLdcInsn(new Long(cst));
+        }
+    }
+
+    public void fconst(final float cst) {
+        int bits = Float.floatToIntBits(cst);
+        if (bits == 0L || bits == 0x3f800000 || bits == 0x40000000) { // 0..2
+            mv.visitInsn(Opcodes.FCONST_0 + (int) cst);
+        } else {
+            mv.visitLdcInsn(new Float(cst));
+        }
+    }
+
+    public void dconst(final double cst) {
+        long bits = Double.doubleToLongBits(cst);
+        if (bits == 0L || bits == 0x3ff0000000000000L) { // +0.0d and 1.0d
+            mv.visitInsn(Opcodes.DCONST_0 + (int) cst);
+        } else {
+            mv.visitLdcInsn(new Double(cst));
+        }
+    }
+
+    public void tconst(final Type type) {
+        mv.visitLdcInsn(type);
+    }
+
+    public void hconst(final Handle handle) {
+        mv.visitLdcInsn(handle);
+    }
+
+    public void load(final int var, final Type type) {
+        mv.visitVarInsn(type.getOpcode(Opcodes.ILOAD), var);
+    }
+
+    public void aload(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IALOAD));
+    }
+
+    public void store(final int var, final Type type) {
+        mv.visitVarInsn(type.getOpcode(Opcodes.ISTORE), var);
+    }
+
+    public void astore(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IASTORE));
+    }
+
+    public void pop() {
+        mv.visitInsn(Opcodes.POP);
+    }
+
+    public void pop2() {
+        mv.visitInsn(Opcodes.POP2);
+    }
+
+    public void dup() {
+        mv.visitInsn(Opcodes.DUP);
+    }
+
+    public void dup2() {
+        mv.visitInsn(Opcodes.DUP2);
+    }
+
+    public void dupX1() {
+        mv.visitInsn(Opcodes.DUP_X1);
+    }
+
+    public void dupX2() {
+        mv.visitInsn(Opcodes.DUP_X2);
+    }
+
+    public void dup2X1() {
+        mv.visitInsn(Opcodes.DUP2_X1);
+    }
+
+    public void dup2X2() {
+        mv.visitInsn(Opcodes.DUP2_X2);
+    }
+
+    public void swap() {
+        mv.visitInsn(Opcodes.SWAP);
+    }
+
+    public void add(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IADD));
+    }
+
+    public void sub(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.ISUB));
+    }
+
+    public void mul(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IMUL));
+    }
+
+    public void div(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IDIV));
+    }
+
+    public void rem(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IREM));
+    }
+
+    public void neg(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.INEG));
+    }
+
+    public void shl(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.ISHL));
+    }
+
+    public void shr(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.ISHR));
+    }
+
+    public void ushr(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IUSHR));
+    }
+
+    public void and(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IAND));
+    }
+
+    public void or(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IOR));
+    }
+
+    public void xor(final Type type) {
+        mv.visitInsn(type.getOpcode(Opcodes.IXOR));
+    }
+
+    public void iinc(final int var, final int increment) {
+        mv.visitIincInsn(var, increment);
+    }
+
+    public void cast(final Type from, final Type to) {
+        if (from != to) {
+            if (from == Type.DOUBLE_TYPE) {
+                if (to == Type.FLOAT_TYPE) {
+                    mv.visitInsn(Opcodes.D2F);
+                } else if (to == Type.LONG_TYPE) {
+                    mv.visitInsn(Opcodes.D2L);
+                } else {
+                    mv.visitInsn(Opcodes.D2I);
+                    cast(Type.INT_TYPE, to);
+                }
+            } else if (from == Type.FLOAT_TYPE) {
+                if (to == Type.DOUBLE_TYPE) {
+                    mv.visitInsn(Opcodes.F2D);
+                } else if (to == Type.LONG_TYPE) {
+                    mv.visitInsn(Opcodes.F2L);
+                } else {
+                    mv.visitInsn(Opcodes.F2I);
+                    cast(Type.INT_TYPE, to);
+                }
+            } else if (from == Type.LONG_TYPE) {
+                if (to == Type.DOUBLE_TYPE) {
+                    mv.visitInsn(Opcodes.L2D);
+                } else if (to == Type.FLOAT_TYPE) {
+                    mv.visitInsn(Opcodes.L2F);
+                } else {
+                    mv.visitInsn(Opcodes.L2I);
+                    cast(Type.INT_TYPE, to);
+                }
+            } else {
+                if (to == Type.BYTE_TYPE) {
+                    mv.visitInsn(Opcodes.I2B);
+                } else if (to == Type.CHAR_TYPE) {
+                    mv.visitInsn(Opcodes.I2C);
+                } else if (to == Type.DOUBLE_TYPE) {
+                    mv.visitInsn(Opcodes.I2D);
+                } else if (to == Type.FLOAT_TYPE) {
+                    mv.visitInsn(Opcodes.I2F);
+                } else if (to == Type.LONG_TYPE) {
+                    mv.visitInsn(Opcodes.I2L);
+                } else if (to == Type.SHORT_TYPE) {
+                    mv.visitInsn(Opcodes.I2S);
+                }
+            }
+        }
+    }
+
+    public void lcmp() {
+        mv.visitInsn(Opcodes.LCMP);
+    }
+
+    public void cmpl(final Type type) {
+        mv.visitInsn(type == Type.FLOAT_TYPE ? Opcodes.FCMPL : Opcodes.DCMPL);
+    }
+
+    public void cmpg(final Type type) {
+        mv.visitInsn(type == Type.FLOAT_TYPE ? Opcodes.FCMPG : Opcodes.DCMPG);
+    }
+
+    public void ifeq(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFEQ, label);
+    }
+
+    public void ifne(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFNE, label);
+    }
+
+    public void iflt(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFLT, label);
+    }
+
+    public void ifge(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFGE, label);
+    }
+
+    public void ifgt(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFGT, label);
+    }
+
+    public void ifle(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFLE, label);
+    }
+
+    public void ificmpeq(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ICMPEQ, label);
+    }
+
+    public void ificmpne(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ICMPNE, label);
+    }
+
+    public void ificmplt(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ICMPLT, label);
+    }
+
+    public void ificmpge(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ICMPGE, label);
+    }
+
+    public void ificmpgt(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ICMPGT, label);
+    }
+
+    public void ificmple(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ICMPLE, label);
+    }
+
+    public void ifacmpeq(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ACMPEQ, label);
+    }
+
+    public void ifacmpne(final Label label) {
+        mv.visitJumpInsn(Opcodes.IF_ACMPNE, label);
+    }
+
+    public void goTo(final Label label) {
+        mv.visitJumpInsn(Opcodes.GOTO, label);
+    }
+
+    public void jsr(final Label label) {
+        mv.visitJumpInsn(Opcodes.JSR, label);
+    }
+
+    public void ret(final int var) {
+        mv.visitVarInsn(Opcodes.RET, var);
+    }
+
+    public void tableswitch(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        mv.visitTableSwitchInsn(min, max, dflt, labels);
+    }
+
+    public void lookupswitch(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        mv.visitLookupSwitchInsn(dflt, keys, labels);
+    }
+
+    public void areturn(final Type t) {
+        mv.visitInsn(t.getOpcode(Opcodes.IRETURN));
+    }
+
+    public void getstatic(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitFieldInsn(Opcodes.GETSTATIC, owner, name, desc);
+    }
+
+    public void putstatic(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitFieldInsn(Opcodes.PUTSTATIC, owner, name, desc);
+    }
+
+    public void getfield(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitFieldInsn(Opcodes.GETFIELD, owner, name, desc);
+    }
+
+    public void putfield(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitFieldInsn(Opcodes.PUTFIELD, owner, name, desc);
+    }
+
+    public void invokevirtual(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitMethodInsn(Opcodes.INVOKEVIRTUAL, owner, name, desc);
+    }
+
+    public void invokespecial(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitMethodInsn(Opcodes.INVOKESPECIAL, owner, name, desc);
+    }
+
+    public void invokestatic(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitMethodInsn(Opcodes.INVOKESTATIC, owner, name, desc);
+    }
+
+    public void invokeinterface(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        mv.visitMethodInsn(Opcodes.INVOKEINTERFACE, owner, name, desc);
+    }
+
+    public void invokedynamic(
+        String name,
+        String desc,
+        Handle bsm,
+        Object[] bsmArgs)
+    {
+        mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+    }
+
+    public void anew(final Type type) {
+        mv.visitTypeInsn(Opcodes.NEW, type.getInternalName());
+    }
+
+    public void newarray(final Type type) {
+        int typ;
+        switch (type.getSort()) {
+            case Type.BOOLEAN:
+                typ = Opcodes.T_BOOLEAN;
+                break;
+            case Type.CHAR:
+                typ = Opcodes.T_CHAR;
+                break;
+            case Type.BYTE:
+                typ = Opcodes.T_BYTE;
+                break;
+            case Type.SHORT:
+                typ = Opcodes.T_SHORT;
+                break;
+            case Type.INT:
+                typ = Opcodes.T_INT;
+                break;
+            case Type.FLOAT:
+                typ = Opcodes.T_FLOAT;
+                break;
+            case Type.LONG:
+                typ = Opcodes.T_LONG;
+                break;
+            case Type.DOUBLE:
+                typ = Opcodes.T_DOUBLE;
+                break;
+            default:
+                mv.visitTypeInsn(Opcodes.ANEWARRAY, type.getInternalName());
+                return;
+        }
+        mv.visitIntInsn(Opcodes.NEWARRAY, typ);
+    }
+
+    public void arraylength() {
+        mv.visitInsn(Opcodes.ARRAYLENGTH);
+    }
+
+    public void athrow() {
+        mv.visitInsn(Opcodes.ATHROW);
+    }
+
+    public void checkcast(final Type type) {
+        mv.visitTypeInsn(Opcodes.CHECKCAST, type.getInternalName());
+    }
+
+    public void instanceOf(final Type type) {
+        mv.visitTypeInsn(Opcodes.INSTANCEOF, type.getInternalName());
+    }
+
+    public void monitorenter() {
+        mv.visitInsn(Opcodes.MONITORENTER);
+    }
+
+    public void monitorexit() {
+        mv.visitInsn(Opcodes.MONITOREXIT);
+    }
+
+    public void multianewarray(final String desc, final int dims) {
+        mv.visitMultiANewArrayInsn(desc, dims);
+    }
+
+    public void ifnull(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFNULL, label);
+    }
+
+    public void ifnonnull(final Label label) {
+        mv.visitJumpInsn(Opcodes.IFNONNULL, label);
+    }
+
+    public void mark(final Label label) {
+        mv.visitLabel(label);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/JSRInlinerAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,770 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.AbstractMap;
+import java.util.ArrayList;
+import java.util.BitSet;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+import jdk.internal.org.objectweb.asm.tree.InsnList;
+import jdk.internal.org.objectweb.asm.tree.InsnNode;
+import jdk.internal.org.objectweb.asm.tree.JumpInsnNode;
+import jdk.internal.org.objectweb.asm.tree.LabelNode;
+import jdk.internal.org.objectweb.asm.tree.LocalVariableNode;
+import jdk.internal.org.objectweb.asm.tree.LookupSwitchInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MethodNode;
+import jdk.internal.org.objectweb.asm.tree.TableSwitchInsnNode;
+import jdk.internal.org.objectweb.asm.tree.TryCatchBlockNode;
+
+/**
+ * A {@link jdk.internal.org.objectweb.asm.MethodVisitor} that removes JSR instructions and
+ * inlines the referenced subroutines.
+ *
+ * <b>Explanation of how it works</b> TODO
+ *
+ * @author Niko Matsakis
+ */
+public class JSRInlinerAdapter extends MethodNode implements Opcodes {
+
+    private static final boolean LOGGING = false;
+
+    /**
+     * For each label that is jumped to by a JSR, we create a BitSet
+     * instance.
+     */
+    private final Map<LabelNode,BitSet> subroutineHeads = new HashMap<LabelNode,BitSet>();
+
+    /**
+     * This subroutine instance denotes the line of execution that is not
+     * contained within any subroutine; i.e., the "subroutine" that is executing
+     * when a method first begins.
+     */
+    private final BitSet mainSubroutine = new BitSet();
+
+    /**
+     * This BitSet contains the index of every instruction that belongs to more
+     * than one subroutine. This should not happen often.
+     */
+    final BitSet dualCitizens = new BitSet();
+
+    /**
+     * Creates a new JSRInliner. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #JSRInlinerAdapter(int, MethodVisitor, int, String, String, String, String[])}
+     * version.
+     *
+     * @param mv the <code>MethodVisitor</code> to send the resulting inlined
+     *        method code to (use <code>null</code> for none).
+     * @param access the method's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the method is synthetic and/or
+     *        deprecated.
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type}).
+     * @param signature the method's signature. May be <tt>null</tt>.
+     * @param exceptions the internal names of the method's exception classes
+     *        (see {@link Type#getInternalName() getInternalName}). May be
+     *        <tt>null</tt>.
+     */
+    public JSRInlinerAdapter(
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        this(Opcodes.ASM4, mv, access, name, desc, signature, exceptions);
+    }
+
+    /**
+     * Creates a new JSRInliner.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param mv the <code>MethodVisitor</code> to send the resulting inlined
+     *        method code to (use <code>null</code> for none).
+     * @param access the method's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the method is synthetic and/or
+     *        deprecated.
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type}).
+     * @param signature the method's signature. May be <tt>null</tt>.
+     * @param exceptions the internal names of the method's exception classes
+     *        (see {@link Type#getInternalName() getInternalName}). May be
+     *        <tt>null</tt>.
+     */
+    protected JSRInlinerAdapter(
+        final int api,
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        super(api, access, name, desc, signature, exceptions);
+        this.mv = mv;
+    }
+
+    /**
+     * Detects a JSR instruction and sets a flag to indicate we will need to do
+     * inlining.
+     */
+    @Override
+    public void visitJumpInsn(final int opcode, final Label lbl) {
+        super.visitJumpInsn(opcode, lbl);
+        LabelNode ln = ((JumpInsnNode) instructions.getLast()).label;
+        if (opcode == JSR && !subroutineHeads.containsKey(ln)) {
+            subroutineHeads.put(ln, new BitSet());
+        }
+    }
+
+    /**
+     * If any JSRs were seen, triggers the inlining process. Otherwise, forwards
+     * the byte codes untouched.
+     */
+    @Override
+    public void visitEnd() {
+        if (!subroutineHeads.isEmpty()) {
+            markSubroutines();
+            if (LOGGING) {
+                log(mainSubroutine.toString());
+                Iterator<BitSet> it = subroutineHeads.values().iterator();
+                while (it.hasNext()) {
+                    BitSet sub = it.next();
+                    log(sub.toString());
+                }
+            }
+            emitCode();
+        }
+
+        // Forward the translate opcodes on if appropriate:
+        if (mv != null) {
+            accept(mv);
+        }
+    }
+
+    /**
+     * Walks the method and determines which internal subroutine(s), if any,
+     * each instruction is a method of.
+     */
+    private void markSubroutines() {
+        BitSet anyvisited = new BitSet();
+
+        // First walk the main subroutine and find all those instructions which
+        // can be reached without invoking any JSR at all
+        markSubroutineWalk(mainSubroutine, 0, anyvisited);
+
+        // Go through the head of each subroutine and find any nodes reachable
+        // to that subroutine without following any JSR links.
+        for (Iterator<Map.Entry<LabelNode,BitSet>> it = subroutineHeads.entrySet().iterator(); it.hasNext();)
+        {
+            Map.Entry<LabelNode,BitSet> entry = it.next();
+            LabelNode lab = entry.getKey();
+            BitSet sub = entry.getValue();
+            int index = instructions.indexOf(lab);
+            markSubroutineWalk(sub, index, anyvisited);
+        }
+    }
+
+    /**
+     * Performs a depth first search walking the normal byte code path starting
+     * at <code>index</code>, and adding each instruction encountered into
+     * the subroutine <code>sub</code>. After this walk is complete, iterates
+     * over the exception handlers to ensure that we also include those byte
+     * codes which are reachable through an exception that may be thrown during
+     * the execution of the subroutine. Invoked from
+     * <code>markSubroutines()</code>.
+     *
+     * @param sub the subroutine whose instructions must be computed.
+     * @param index an instruction of this subroutine.
+     * @param anyvisited indexes of the already visited instructions, i.e.
+     *        marked as part of this subroutine or any previously computed
+     *        subroutine.
+     */
+    private void markSubroutineWalk(
+        final BitSet sub,
+        final int index,
+        final BitSet anyvisited)
+    {
+        if (LOGGING) {
+            log("markSubroutineWalk: sub=" + sub + " index=" + index);
+        }
+
+        // First find those instructions reachable via normal execution
+        markSubroutineWalkDFS(sub, index, anyvisited);
+
+        // Now, make sure we also include any applicable exception handlers
+        boolean loop = true;
+        while (loop) {
+            loop = false;
+            for (Iterator<TryCatchBlockNode> it = tryCatchBlocks.iterator(); it.hasNext();) {
+                TryCatchBlockNode trycatch = it.next();
+
+                if (LOGGING) {
+                    // TODO use of default toString().
+                    log("Scanning try/catch " + trycatch);
+                }
+
+                // If the handler has already been processed, skip it.
+                int handlerindex = instructions.indexOf(trycatch.handler);
+                if (sub.get(handlerindex)) {
+                    continue;
+                }
+
+                int startindex = instructions.indexOf(trycatch.start);
+                int endindex = instructions.indexOf(trycatch.end);
+                int nextbit = sub.nextSetBit(startindex);
+                if (nextbit != -1 && nextbit < endindex) {
+                    if (LOGGING) {
+                        log("Adding exception handler: " + startindex + '-'
+                                + endindex + " due to " + nextbit + " handler "
+                                + handlerindex);
+                    }
+                    markSubroutineWalkDFS(sub, handlerindex, anyvisited);
+                    loop = true;
+                }
+            }
+        }
+    }
+
+    /**
+     * Performs a simple DFS of the instructions, assigning each to the
+     * subroutine <code>sub</code>. Starts from <code>index</code>.
+     * Invoked only by <code>markSubroutineWalk()</code>.
+     *
+     * @param sub the subroutine whose instructions must be computed.
+     * @param index an instruction of this subroutine.
+     * @param anyvisited indexes of the already visited instructions, i.e.
+     *        marked as part of this subroutine or any previously computed
+     *        subroutine.
+     */
+    private void markSubroutineWalkDFS(
+        final BitSet sub,
+        int index,
+        final BitSet anyvisited)
+    {
+        while (true) {
+            AbstractInsnNode node = instructions.get(index);
+
+            // don't visit a node twice
+            if (sub.get(index)) {
+                return;
+            }
+            sub.set(index);
+
+            // check for those nodes already visited by another subroutine
+            if (anyvisited.get(index)) {
+                dualCitizens.set(index);
+                if (LOGGING) {
+                    log("Instruction #" + index + " is dual citizen.");
+                }
+            }
+            anyvisited.set(index);
+
+            if (node.getType() == AbstractInsnNode.JUMP_INSN
+                    && node.getOpcode() != JSR)
+            {
+                // we do not follow recursively called subroutines here; but any
+                // other sort of branch we do follow
+                JumpInsnNode jnode = (JumpInsnNode) node;
+                int destidx = instructions.indexOf(jnode.label);
+                markSubroutineWalkDFS(sub, destidx, anyvisited);
+            }
+            if (node.getType() == AbstractInsnNode.TABLESWITCH_INSN) {
+                TableSwitchInsnNode tsnode = (TableSwitchInsnNode) node;
+                int destidx = instructions.indexOf(tsnode.dflt);
+                markSubroutineWalkDFS(sub, destidx, anyvisited);
+                for (int i = tsnode.labels.size() - 1; i >= 0; --i) {
+                    LabelNode l = tsnode.labels.get(i);
+                    destidx = instructions.indexOf(l);
+                    markSubroutineWalkDFS(sub, destidx, anyvisited);
+                }
+            }
+            if (node.getType() == AbstractInsnNode.LOOKUPSWITCH_INSN) {
+                LookupSwitchInsnNode lsnode = (LookupSwitchInsnNode) node;
+                int destidx = instructions.indexOf(lsnode.dflt);
+                markSubroutineWalkDFS(sub, destidx, anyvisited);
+                for (int i = lsnode.labels.size() - 1; i >= 0; --i) {
+                    LabelNode l = lsnode.labels.get(i);
+                    destidx = instructions.indexOf(l);
+                    markSubroutineWalkDFS(sub, destidx, anyvisited);
+                }
+            }
+
+            // check to see if this opcode falls through to the next instruction
+            // or not; if not, return.
+            switch (instructions.get(index).getOpcode()) {
+                case GOTO:
+                case RET:
+                case TABLESWITCH:
+                case LOOKUPSWITCH:
+                case IRETURN:
+                case LRETURN:
+                case FRETURN:
+                case DRETURN:
+                case ARETURN:
+                case RETURN:
+                case ATHROW:
+                    /*
+                     * note: this either returns from this subroutine, or a
+                     * parent subroutine which invoked it
+                     */
+                    return;
+            }
+
+            // Use tail recursion here in the form of an outer while loop to
+            // avoid our stack growing needlessly:
+            index++;
+        }
+    }
+
+    /**
+     * Creates the new instructions, inlining each instantiation of each
+     * subroutine until the code is fully elaborated.
+     */
+    private void emitCode() {
+        LinkedList<Instantiation> worklist = new LinkedList<Instantiation>();
+        // Create an instantiation of the "root" subroutine, which is just the
+        // main routine
+        worklist.add(new Instantiation(null, mainSubroutine));
+
+        // Emit instantiations of each subroutine we encounter, including the
+        // main subroutine
+        InsnList newInstructions = new InsnList();
+        List<TryCatchBlockNode> newTryCatchBlocks = new ArrayList<TryCatchBlockNode>();
+        List<LocalVariableNode> newLocalVariables = new ArrayList<LocalVariableNode>();
+        while (!worklist.isEmpty()) {
+            Instantiation inst = worklist.removeFirst();
+            emitSubroutine(inst,
+                    worklist,
+                    newInstructions,
+                    newTryCatchBlocks,
+                    newLocalVariables);
+        }
+        instructions = newInstructions;
+        tryCatchBlocks = newTryCatchBlocks;
+        localVariables = newLocalVariables;
+    }
+
+    /**
+     * Emits one instantiation of one subroutine, specified by
+     * <code>instant</code>. May add new instantiations that are invoked by
+     * this one to the <code>worklist</code> parameter, and new try/catch
+     * blocks to <code>newTryCatchBlocks</code>.
+     *
+     * @param instant the instantiation that must be performed.
+     * @param worklist list of the instantiations that remain to be done.
+     * @param newInstructions the instruction list to which the instantiated
+     *        code must be appended.
+     * @param newTryCatchBlocks the exception handler list to which the
+     *        instantiated handlers must be appended.
+     */
+    private void emitSubroutine(
+        final Instantiation instant,
+        final List<Instantiation> worklist,
+        final InsnList newInstructions,
+        final List<TryCatchBlockNode> newTryCatchBlocks,
+        final List<LocalVariableNode> newLocalVariables)
+    {
+        LabelNode duplbl = null;
+
+        if (LOGGING) {
+            log("--------------------------------------------------------");
+            log("Emitting instantiation of subroutine " + instant.subroutine);
+        }
+
+        // Emit the relevant instructions for this instantiation, translating
+        // labels and jump targets as we go:
+        for (int i = 0, c = instructions.size(); i < c; i++) {
+            AbstractInsnNode insn = instructions.get(i);
+            Instantiation owner = instant.findOwner(i);
+
+            // Always remap labels:
+            if (insn.getType() == AbstractInsnNode.LABEL) {
+                // Translate labels into their renamed equivalents.
+                // Avoid adding the same label more than once. Note
+                // that because we own this instruction the gotoTable
+                // and the rangeTable will always agree.
+                LabelNode ilbl = (LabelNode) insn;
+                LabelNode remap = instant.rangeLabel(ilbl);
+                if (LOGGING) {
+                    // TODO use of default toString().
+                    log("Translating lbl #" + i + ':' + ilbl + " to " + remap);
+                }
+                if (remap != duplbl) {
+                    newInstructions.add(remap);
+                    duplbl = remap;
+                }
+                continue;
+            }
+
+            // We don't want to emit instructions that were already
+            // emitted by a subroutine higher on the stack. Note that
+            // it is still possible for a given instruction to be
+            // emitted twice because it may belong to two subroutines
+            // that do not invoke each other.
+            if (owner != instant) {
+                continue;
+            }
+
+            if (LOGGING) {
+                log("Emitting inst #" + i);
+            }
+
+            if (insn.getOpcode() == RET) {
+                // Translate RET instruction(s) to a jump to the return label
+                // for the appropriate instantiation. The problem is that the
+                // subroutine may "fall through" to the ret of a parent
+                // subroutine; therefore, to find the appropriate ret label we
+                // find the lowest subroutine on the stack that claims to own
+                // this instruction. See the class javadoc comment for an
+                // explanation on why this technique is safe (note: it is only
+                // safe if the input is verifiable).
+                LabelNode retlabel = null;
+                for (Instantiation p = instant; p != null; p = p.previous) {
+                    if (p.subroutine.get(i)) {
+                        retlabel = p.returnLabel;
+                    }
+                }
+                if (retlabel == null) {
+                    // This is only possible if the mainSubroutine owns a RET
+                    // instruction, which should never happen for verifiable
+                    // code.
+                    throw new RuntimeException("Instruction #" + i
+                            + " is a RET not owned by any subroutine");
+                }
+                newInstructions.add(new JumpInsnNode(GOTO, retlabel));
+            } else if (insn.getOpcode() == JSR) {
+                LabelNode lbl = ((JumpInsnNode) insn).label;
+                BitSet sub = subroutineHeads.get(lbl);
+                Instantiation newinst = new Instantiation(instant, sub);
+                LabelNode startlbl = newinst.gotoLabel(lbl);
+
+                if (LOGGING) {
+                    log(" Creating instantiation of subr " + sub);
+                }
+
+                // Rather than JSRing, we will jump to the inline version and
+                // push NULL for what was once the return value. This hack
+                // allows us to avoid doing any sort of data flow analysis to
+                // figure out which instructions manipulate the old return value
+                // pointer which is now known to be unneeded.
+                newInstructions.add(new InsnNode(ACONST_NULL));
+                newInstructions.add(new JumpInsnNode(GOTO, startlbl));
+                newInstructions.add(newinst.returnLabel);
+
+                // Insert this new instantiation into the queue to be emitted
+                // later.
+                worklist.add(newinst);
+            } else {
+                newInstructions.add(insn.clone(instant));
+            }
+        }
+
+        // Emit try/catch blocks that are relevant to this method.
+        for (Iterator<TryCatchBlockNode> it = tryCatchBlocks.iterator(); it.hasNext();) {
+            TryCatchBlockNode trycatch = it.next();
+
+            if (LOGGING) {
+                // TODO use of default toString().
+                log("try catch block original labels=" + trycatch.start + '-'
+                        + trycatch.end + "->" + trycatch.handler);
+            }
+
+            final LabelNode start = instant.rangeLabel(trycatch.start);
+            final LabelNode end = instant.rangeLabel(trycatch.end);
+
+            // Ignore empty try/catch regions
+            if (start == end) {
+                if (LOGGING) {
+                    log(" try catch block empty in this subroutine");
+                }
+                continue;
+            }
+
+            final LabelNode handler = instant.gotoLabel(trycatch.handler);
+
+            if (LOGGING) {
+                // TODO use of default toString().
+                log(" try catch block new labels=" + start + '-' + end + "->"
+                        + handler);
+            }
+
+            if (start == null || end == null || handler == null) {
+                throw new RuntimeException("Internal error!");
+            }
+
+            newTryCatchBlocks.add(new TryCatchBlockNode(start,
+                    end,
+                    handler,
+                    trycatch.type));
+        }
+
+        for (Iterator<LocalVariableNode> it = localVariables.iterator(); it.hasNext();) {
+            LocalVariableNode lvnode = it.next();
+            if (LOGGING) {
+                log("local var " + lvnode.name);
+            }
+            final LabelNode start = instant.rangeLabel(lvnode.start);
+            final LabelNode end = instant.rangeLabel(lvnode.end);
+            if (start == end) {
+                if (LOGGING) {
+                    log("  local variable empty in this sub");
+                }
+                continue;
+            }
+            newLocalVariables.add(new LocalVariableNode(lvnode.name,
+                    lvnode.desc,
+                    lvnode.signature,
+                    start,
+                    end,
+                    lvnode.index));
+        }
+    }
+
+    private static void log(final String str) {
+        System.err.println(str);
+    }
+
+    /**
+     * A class that represents an instantiation of a subroutine. Each
+     * instantiation has an associate "stack" --- which is a listing of those
+     * instantiations that were active when this particular instance of this
+     * subroutine was invoked. Each instantiation also has a map from the
+     * original labels of the program to the labels appropriate for this
+     * instantiation, and finally a label to return to.
+     */
+    private class Instantiation extends AbstractMap<LabelNode, LabelNode> {
+
+        /**
+         * Previous instantiations; the stack must be statically predictable to
+         * be inlinable.
+         */
+        final Instantiation previous;
+
+        /**
+         * The subroutine this is an instantiation of.
+         */
+        public final BitSet subroutine;
+
+        /**
+         * This table maps Labels from the original source to Labels pointing at
+         * code specific to this instantiation, for use in remapping try/catch
+         * blocks,as well as gotos.
+         *
+         * Note that in the presence of dual citizens instructions, that is,
+         * instructions which belong to more than one subroutine due to the
+         * merging of control flow without a RET instruction, we will map the
+         * target label of a GOTO to the label used by the instantiation lowest
+         * on the stack. This avoids code duplication during inlining in most
+         * cases.
+         *
+         * @see #findOwner(int)
+         */
+        public final Map<LabelNode, LabelNode> rangeTable = new HashMap<LabelNode, LabelNode>();
+
+        /**
+         * All returns for this instantiation will be mapped to this label
+         */
+        public final LabelNode returnLabel;
+
+        Instantiation(final Instantiation prev, final BitSet sub) {
+            previous = prev;
+            subroutine = sub;
+            for (Instantiation p = prev; p != null; p = p.previous) {
+                if (p.subroutine == sub) {
+                    throw new RuntimeException("Recursive invocation of " + sub);
+                }
+            }
+
+            // Determine the label to return to when this subroutine terminates
+            // via RET: note that the main subroutine never terminates via RET.
+            if (prev != null) {
+                returnLabel = new LabelNode();
+            } else {
+                returnLabel = null;
+            }
+
+            // Each instantiation will remap the labels from the code above to
+            // refer to its particular copy of its own instructions. Note that
+            // we collapse labels which point at the same instruction into one:
+            // this is fairly common as we are often ignoring large chunks of
+            // instructions, so what were previously distinct labels become
+            // duplicates.
+            LabelNode duplbl = null;
+            for (int i = 0, c = instructions.size(); i < c; i++) {
+                AbstractInsnNode insn = instructions.get(i);
+
+                if (insn.getType() == AbstractInsnNode.LABEL) {
+                    LabelNode ilbl = (LabelNode) insn;
+
+                    if (duplbl == null) {
+                        // if we already have a label pointing at this spot,
+                        // don't recreate it.
+                        duplbl = new LabelNode();
+                    }
+
+                    // Add an entry in the rangeTable for every label
+                    // in the original code which points at the next
+                    // instruction of our own to be emitted.
+                    rangeTable.put(ilbl, duplbl);
+                } else if (findOwner(i) == this) {
+                    // We will emit this instruction, so clear the 'duplbl' flag
+                    // since the next Label will refer to a distinct
+                    // instruction.
+                    duplbl = null;
+                }
+            }
+        }
+
+        /**
+         * Returns the "owner" of a particular instruction relative to this
+         * instantiation: the owner referes to the Instantiation which will emit
+         * the version of this instruction that we will execute.
+         *
+         * Typically, the return value is either <code>this</code> or
+         * <code>null</code>. <code>this</code> indicates that this
+         * instantiation will generate the version of this instruction that we
+         * will execute, and <code>null</code> indicates that this
+         * instantiation never executes the given instruction.
+         *
+         * Sometimes, however, an instruction can belong to multiple
+         * subroutines; this is called a "dual citizen" instruction (though it
+         * may belong to more than 2 subroutines), and occurs when multiple
+         * subroutines branch to common points of control. In this case, the
+         * owner is the subroutine that appears lowest on the stack, and which
+         * also owns the instruction in question.
+         *
+         * @param i the index of the instruction in the original code
+         * @return the "owner" of a particular instruction relative to this
+         *         instantiation.
+         */
+        public Instantiation findOwner(final int i) {
+            if (!subroutine.get(i)) {
+                return null;
+            }
+            if (!dualCitizens.get(i)) {
+                return this;
+            }
+            Instantiation own = this;
+            for (Instantiation p = previous; p != null; p = p.previous) {
+                if (p.subroutine.get(i)) {
+                    own = p;
+                }
+            }
+            return own;
+        }
+
+        /**
+         * Looks up the label <code>l</code> in the <code>gotoTable</code>,
+         * thus translating it from a Label in the original code, to a Label in
+         * the inlined code that is appropriate for use by an instruction that
+         * branched to the original label.
+         *
+         * @param l The label we will be translating
+         * @return a label for use by a branch instruction in the inlined code
+         * @see #rangeLabel
+         */
+        public LabelNode gotoLabel(final LabelNode l) {
+            // owner should never be null, because owner is only null
+            // if an instruction cannot be reached from this subroutine
+            Instantiation owner = findOwner(instructions.indexOf(l));
+            return owner.rangeTable.get(l);
+        }
+
+        /**
+         * Looks up the label <code>l</code> in the <code>rangeTable</code>,
+         * thus translating it from a Label in the original code, to a Label in
+         * the inlined code that is appropriate for use by an try/catch or
+         * variable use annotation.
+         *
+         * @param l The label we will be translating
+         * @return a label for use by a try/catch or variable annotation in the
+         *         original code
+         * @see #rangeTable
+         */
+        public LabelNode rangeLabel(final LabelNode l) {
+            return rangeTable.get(l);
+        }
+
+        // AbstractMap implementation
+
+        @Override
+        public Set<Map.Entry<LabelNode, LabelNode>> entrySet() {
+            return null;
+        }
+
+        @Override
+        public LabelNode get(final Object o) {
+            return gotoLabel((LabelNode) o);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/LocalVariablesSorter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,371 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link MethodVisitor} that renumbers local variables in their order of
+ * appearance. This adapter allows one to easily add new local variables to a
+ * method. It may be used by inheriting from this class, but the preferred way
+ * of using it is via delegation: the next visitor in the chain can indeed add
+ * new locals when needed by calling {@link #newLocal} on this adapter (this
+ * requires a reference back to this {@link LocalVariablesSorter}).
+ *
+ * @author Chris Nokleberg
+ * @author Eugene Kuleshov
+ * @author Eric Bruneton
+ */
+public class LocalVariablesSorter extends MethodVisitor {
+
+    private static final Type OBJECT_TYPE = Type.getObjectType("java/lang/Object");
+
+    /**
+     * Mapping from old to new local variable indexes. A local variable at index
+     * i of size 1 is remapped to 'mapping[2*i]', while a local variable at
+     * index i of size 2 is remapped to 'mapping[2*i+1]'.
+     */
+    private int[] mapping = new int[40];
+
+    /**
+     * Array used to store stack map local variable types after remapping.
+     */
+    private Object[] newLocals = new Object[20];
+
+    /**
+     * Index of the first local variable, after formal parameters.
+     */
+    protected final int firstLocal;
+
+    /**
+     * Index of the next local variable to be created by {@link #newLocal}.
+     */
+    protected int nextLocal;
+
+    /**
+     * Indicates if at least one local variable has moved due to remapping.
+     */
+    private boolean changed;
+
+    /**
+     * Creates a new {@link LocalVariablesSorter}. <i>Subclasses must not use
+     * this constructor</i>. Instead, they must use the
+     * {@link #LocalVariablesSorter(int, int, String, MethodVisitor)} version.
+     *
+     * @param access access flags of the adapted method.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param mv the method visitor to which this adapter delegates calls.
+     */
+    public LocalVariablesSorter(
+        final int access,
+        final String desc,
+        final MethodVisitor mv)
+    {
+        this(Opcodes.ASM4, access, desc, mv);
+    }
+
+    /**
+     * Creates a new {@link LocalVariablesSorter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param access access flags of the adapted method.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param mv the method visitor to which this adapter delegates calls.
+     */
+    protected LocalVariablesSorter(
+        final int api,
+        final int access,
+        final String desc,
+        final MethodVisitor mv)
+    {
+        super(api, mv);
+        Type[] args = Type.getArgumentTypes(desc);
+        nextLocal = (Opcodes.ACC_STATIC & access) == 0 ? 1 : 0;
+        for (int i = 0; i < args.length; i++) {
+            nextLocal += args[i].getSize();
+        }
+        firstLocal = nextLocal;
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        Type type;
+        switch (opcode) {
+            case Opcodes.LLOAD:
+            case Opcodes.LSTORE:
+                type = Type.LONG_TYPE;
+                break;
+
+            case Opcodes.DLOAD:
+            case Opcodes.DSTORE:
+                type = Type.DOUBLE_TYPE;
+                break;
+
+            case Opcodes.FLOAD:
+            case Opcodes.FSTORE:
+                type = Type.FLOAT_TYPE;
+                break;
+
+            case Opcodes.ILOAD:
+            case Opcodes.ISTORE:
+                type = Type.INT_TYPE;
+                break;
+
+            default:
+            // case Opcodes.ALOAD:
+            // case Opcodes.ASTORE:
+            // case RET:
+                type = OBJECT_TYPE;
+                break;
+        }
+        mv.visitVarInsn(opcode, remap(var, type));
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        mv.visitIincInsn(remap(var, Type.INT_TYPE), increment);
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        mv.visitMaxs(maxStack, nextLocal);
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        int newIndex = remap(index, Type.getType(desc));
+        mv.visitLocalVariable(name, desc, signature, start, end, newIndex);
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        if (type != Opcodes.F_NEW) { // uncompressed frame
+            throw new IllegalStateException("ClassReader.accept() should be called with EXPAND_FRAMES flag");
+        }
+
+        if (!changed) { // optimization for the case where mapping = identity
+            mv.visitFrame(type, nLocal, local, nStack, stack);
+            return;
+        }
+
+        // creates a copy of newLocals
+        Object[] oldLocals = new Object[newLocals.length];
+        System.arraycopy(newLocals, 0, oldLocals, 0, oldLocals.length);
+
+        // copies types from 'local' to 'newLocals'
+        // 'newLocals' already contains the variables added with 'newLocal'
+
+        int index = 0; // old local variable index
+        int number = 0; // old local variable number
+        for (; number < nLocal; ++number) {
+            Object t = local[number];
+            int size = t == Opcodes.LONG || t == Opcodes.DOUBLE ? 2 : 1;
+            if (t != Opcodes.TOP) {
+                Type typ = OBJECT_TYPE;
+                if (t == Opcodes.INTEGER) {
+                    typ = Type.INT_TYPE;
+                } else if (t == Opcodes.FLOAT) {
+                    typ = Type.FLOAT_TYPE;
+                } else if (t == Opcodes.LONG) {
+                    typ = Type.LONG_TYPE;
+                } else if (t == Opcodes.DOUBLE) {
+                    typ = Type.DOUBLE_TYPE;
+                } else if (t instanceof String) {
+                    typ = Type.getObjectType((String) t);
+                }
+                setFrameLocal(remap(index, typ), t);
+            }
+            index += size;
+        }
+
+        // removes TOP after long and double types as well as trailing TOPs
+
+        index = 0;
+        number = 0;
+        for (int i = 0; index < newLocals.length; ++i) {
+            Object t = newLocals[index++];
+            if (t != null && t != Opcodes.TOP) {
+                newLocals[i] = t;
+                number = i + 1;
+                if (t == Opcodes.LONG || t == Opcodes.DOUBLE) {
+                    index += 1;
+                }
+            } else {
+                newLocals[i] = Opcodes.TOP;
+            }
+        }
+
+        // visits remapped frame
+        mv.visitFrame(type, number, newLocals, nStack, stack);
+
+        // restores original value of 'newLocals'
+        newLocals = oldLocals;
+    }
+
+    // -------------
+
+    /**
+     * Creates a new local variable of the given type.
+     *
+     * @param type the type of the local variable to be created.
+     * @return the identifier of the newly created local variable.
+     */
+    public int newLocal(final Type type) {
+        Object t;
+        switch (type.getSort()) {
+            case Type.BOOLEAN:
+            case Type.CHAR:
+            case Type.BYTE:
+            case Type.SHORT:
+            case Type.INT:
+                t = Opcodes.INTEGER;
+                break;
+            case Type.FLOAT:
+                t = Opcodes.FLOAT;
+                break;
+            case Type.LONG:
+                t = Opcodes.LONG;
+                break;
+            case Type.DOUBLE:
+                t = Opcodes.DOUBLE;
+                break;
+            case Type.ARRAY:
+                t = type.getDescriptor();
+                break;
+            // case Type.OBJECT:
+            default:
+                t = type.getInternalName();
+                break;
+        }
+        int local = nextLocal;
+        nextLocal += type.getSize();
+        setLocalType(local, type);
+        setFrameLocal(local, t);
+        return local;
+    }
+
+    /**
+     * Sets the current type of the given local variable. The default
+     * implementation of this method does nothing.
+     *
+     * @param local a local variable identifier, as returned by {@link #newLocal
+     *        newLocal()}.
+     * @param type the type of the value being stored in the local variable
+     */
+    protected void setLocalType(final int local, final Type type) {
+    }
+
+    private void setFrameLocal(final int local, final Object type) {
+        int l = newLocals.length;
+        if (local >= l) {
+            Object[] a = new Object[Math.max(2 * l, local + 1)];
+            System.arraycopy(newLocals, 0, a, 0, l);
+            newLocals = a;
+        }
+        newLocals[local] = type;
+    }
+
+    private int remap(final int var, final Type type) {
+        if (var + type.getSize() <= firstLocal) {
+            return var;
+        }
+        int key = 2 * var + type.getSize() - 1;
+        int size = mapping.length;
+        if (key >= size) {
+            int[] newMapping = new int[Math.max(2 * size, key + 1)];
+            System.arraycopy(mapping, 0, newMapping, 0, size);
+            mapping = newMapping;
+        }
+        int value = mapping[key];
+        if (value == 0) {
+            value = newLocalMapping(type);
+            setLocalType(value, type);
+            mapping[key] = value + 1;
+        } else {
+            value--;
+        }
+        if (value != var) {
+            changed = true;
+        }
+        return value;
+    }
+
+    protected int newLocalMapping(final Type type) {
+        int local = nextLocal;
+        nextLocal += type.getSize();
+        return local;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/Method.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,307 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A named method descriptor.
+ *
+ * @author Juozas Baliuka
+ * @author Chris Nokleberg
+ * @author Eric Bruneton
+ */
+public class Method {
+
+    /**
+     * The method name.
+     */
+    private final String name;
+
+    /**
+     * The method descriptor.
+     */
+    private final String desc;
+
+    /**
+     * Maps primitive Java type names to their descriptors.
+     */
+    private static final Map<String, String> DESCRIPTORS;
+
+    static {
+        DESCRIPTORS = new HashMap<String, String>();
+        DESCRIPTORS.put("void", "V");
+        DESCRIPTORS.put("byte", "B");
+        DESCRIPTORS.put("char", "C");
+        DESCRIPTORS.put("double", "D");
+        DESCRIPTORS.put("float", "F");
+        DESCRIPTORS.put("int", "I");
+        DESCRIPTORS.put("long", "J");
+        DESCRIPTORS.put("short", "S");
+        DESCRIPTORS.put("boolean", "Z");
+    }
+
+    /**
+     * Creates a new {@link Method}.
+     *
+     * @param name the method's name.
+     * @param desc the method's descriptor.
+     */
+    public Method(final String name, final String desc) {
+        this.name = name;
+        this.desc = desc;
+    }
+
+    /**
+     * Creates a new {@link Method}.
+     *
+     * @param name the method's name.
+     * @param returnType the method's return type.
+     * @param argumentTypes the method's argument types.
+     */
+    public Method(
+        final String name,
+        final Type returnType,
+        final Type[] argumentTypes)
+    {
+        this(name, Type.getMethodDescriptor(returnType, argumentTypes));
+    }
+
+    /**
+     * Creates a new {@link Method}.
+     *
+     * @param m a java.lang.reflect method descriptor
+     * @return a {@link Method} corresponding to the given Java method
+     *         declaration.
+     */
+    public static Method getMethod(java.lang.reflect.Method m) {
+        return new Method(m.getName(), Type.getMethodDescriptor(m));
+    }
+
+    /**
+     * Creates a new {@link Method}.
+     *
+     * @param c a java.lang.reflect constructor descriptor
+     * @return a {@link Method} corresponding to the given Java constructor
+     *         declaration.
+     */
+    public static Method getMethod(java.lang.reflect.Constructor<?> c) {
+        return new Method("<init>", Type.getConstructorDescriptor(c));
+    }
+
+    /**
+     * Returns a {@link Method} corresponding to the given Java method
+     * declaration.
+     *
+     * @param method a Java method declaration, without argument names, of the
+     *        form "returnType name (argumentType1, ... argumentTypeN)", where
+     *        the types are in plain Java (e.g. "int", "float",
+     *        "java.util.List", ...). Classes of the java.lang package can be
+     *        specified by their unqualified name; all other classes names must
+     *        be fully qualified.
+     * @return a {@link Method} corresponding to the given Java method
+     *         declaration.
+     * @throws IllegalArgumentException if <code>method</code> could not get
+     *         parsed.
+     */
+    public static Method getMethod(final String method)
+            throws IllegalArgumentException
+    {
+        return getMethod(method, false);
+    }
+
+    /**
+     * Returns a {@link Method} corresponding to the given Java method
+     * declaration.
+     *
+     * @param method a Java method declaration, without argument names, of the
+     *        form "returnType name (argumentType1, ... argumentTypeN)", where
+     *        the types are in plain Java (e.g. "int", "float",
+     *        "java.util.List", ...). Classes of the java.lang package may be
+     *        specified by their unqualified name, depending on the
+     *        defaultPackage argument; all other classes names must be fully
+     *        qualified.
+     * @param defaultPackage true if unqualified class names belong to the
+     *        default package, or false if they correspond to java.lang classes.
+     *        For instance "Object" means "Object" if this option is true, or
+     *        "java.lang.Object" otherwise.
+     * @return a {@link Method} corresponding to the given Java method
+     *         declaration.
+     * @throws IllegalArgumentException if <code>method</code> could not get
+     *         parsed.
+     */
+    public static Method getMethod(
+        final String method,
+        final boolean defaultPackage) throws IllegalArgumentException
+    {
+        int space = method.indexOf(' ');
+        int start = method.indexOf('(', space) + 1;
+        int end = method.indexOf(')', start);
+        if (space == -1 || start == -1 || end == -1) {
+            throw new IllegalArgumentException();
+        }
+        String returnType = method.substring(0, space);
+        String methodName = method.substring(space + 1, start - 1).trim();
+        StringBuffer sb = new StringBuffer();
+        sb.append('(');
+        int p;
+        do {
+            String s;
+            p = method.indexOf(',', start);
+            if (p == -1) {
+                s = map(method.substring(start, end).trim(), defaultPackage);
+            } else {
+                s = map(method.substring(start, p).trim(), defaultPackage);
+                start = p + 1;
+            }
+            sb.append(s);
+        } while (p != -1);
+        sb.append(')');
+        sb.append(map(returnType, defaultPackage));
+        return new Method(methodName, sb.toString());
+    }
+
+    private static String map(final String type, final boolean defaultPackage) {
+        if ("".equals(type)) {
+            return type;
+        }
+
+        StringBuffer sb = new StringBuffer();
+        int index = 0;
+        while ((index = type.indexOf("[]", index) + 1) > 0) {
+            sb.append('[');
+        }
+
+        String t = type.substring(0, type.length() - sb.length() * 2);
+        String desc = DESCRIPTORS.get(t);
+        if (desc != null) {
+            sb.append(desc);
+        } else {
+            sb.append('L');
+            if (t.indexOf('.') < 0) {
+                if (!defaultPackage) {
+                    sb.append("java/lang/");
+                }
+                sb.append(t);
+            } else {
+                sb.append(t.replace('.', '/'));
+            }
+            sb.append(';');
+        }
+        return sb.toString();
+    }
+
+    /**
+     * Returns the name of the method described by this object.
+     *
+     * @return the name of the method described by this object.
+     */
+    public String getName() {
+        return name;
+    }
+
+    /**
+     * Returns the descriptor of the method described by this object.
+     *
+     * @return the descriptor of the method described by this object.
+     */
+    public String getDescriptor() {
+        return desc;
+    }
+
+    /**
+     * Returns the return type of the method described by this object.
+     *
+     * @return the return type of the method described by this object.
+     */
+    public Type getReturnType() {
+        return Type.getReturnType(desc);
+    }
+
+    /**
+     * Returns the argument types of the method described by this object.
+     *
+     * @return the argument types of the method described by this object.
+     */
+    public Type[] getArgumentTypes() {
+        return Type.getArgumentTypes(desc);
+    }
+
+    @Override
+    public String toString() {
+        return name + desc;
+    }
+
+    @Override
+    public boolean equals(final Object o) {
+        if (!(o instanceof Method)) {
+            return false;
+        }
+        Method other = (Method) o;
+        return name.equals(other.name) && desc.equals(other.desc);
+    }
+
+    @Override
+    public int hashCode() {
+        return name.hashCode() ^ desc.hashCode();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/Remapper.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,250 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.signature.SignatureReader;
+import jdk.internal.org.objectweb.asm.signature.SignatureVisitor;
+import jdk.internal.org.objectweb.asm.signature.SignatureWriter;
+
+/**
+ * A class responsible for remapping types and names.
+ * Subclasses can override the following methods:
+ *
+ * <ul>
+ * <li>{@link #map(String)} - map type</li>
+ * <li>{@link #mapFieldName(String, String, String)} - map field name</li>
+ * <li>{@link #mapMethodName(String, String, String)} - map method name</li>
+ * </ul>
+ *
+ * @author Eugene Kuleshov
+ */
+public abstract class Remapper {
+
+    public String mapDesc(String desc) {
+        Type t = Type.getType(desc);
+        switch (t.getSort()) {
+            case Type.ARRAY:
+                String s = mapDesc(t.getElementType().getDescriptor());
+                for (int i = 0; i < t.getDimensions(); ++i) {
+                    s = '[' + s;
+                }
+                return s;
+            case Type.OBJECT:
+                String newType = map(t.getInternalName());
+                if (newType != null) {
+                    return 'L' + newType + ';';
+                }
+        }
+        return desc;
+    }
+
+    private Type mapType(Type t) {
+        switch (t.getSort()) {
+            case Type.ARRAY:
+                String s = mapDesc(t.getElementType().getDescriptor());
+                for (int i = 0; i < t.getDimensions(); ++i) {
+                    s = '[' + s;
+                }
+                return Type.getType(s);
+            case Type.OBJECT:
+                s = map(t.getInternalName());
+                return s != null ? Type.getObjectType(s) : t;
+            case Type.METHOD:
+                return Type.getMethodType(mapMethodDesc(t.getDescriptor()));
+        }
+        return t;
+    }
+
+    public String mapType(String type) {
+        if (type == null) {
+            return null;
+        }
+        return mapType(Type.getObjectType(type)).getInternalName();
+    }
+
+    public String[] mapTypes(String[] types) {
+        String[] newTypes = null;
+        boolean needMapping = false;
+        for (int i = 0; i < types.length; i++) {
+            String type = types[i];
+            String newType = map(type);
+            if (newType != null && newTypes == null) {
+                newTypes = new String[types.length];
+                if (i > 0) {
+                    System.arraycopy(types, 0, newTypes, 0, i);
+                }
+                needMapping = true;
+            }
+            if (needMapping) {
+                newTypes[i] = newType == null
+                    ? type
+                    : newType;
+            }
+        }
+        return needMapping
+           ? newTypes
+           : types;
+    }
+
+    public String mapMethodDesc(String desc) {
+        if("()V".equals(desc)) {
+            return desc;
+        }
+
+        Type[] args = Type.getArgumentTypes(desc);
+        StringBuffer s = new StringBuffer("(");
+        for (int i = 0; i < args.length; i++) {
+            s.append(mapDesc(args[i].getDescriptor()));
+        }
+        Type returnType = Type.getReturnType(desc);
+        if(returnType == Type.VOID_TYPE) {
+            s.append(")V");
+            return s.toString();
+        }
+        s.append(')').append(mapDesc(returnType.getDescriptor()));
+        return s.toString();
+    }
+
+    public Object mapValue(Object value) {
+        if (value instanceof Type) {
+            return mapType((Type) value);
+        }
+        if (value instanceof Handle) {
+            Handle h = (Handle) value;
+            return new Handle(h.getTag(),
+                    mapType(h.getOwner()),
+                    mapMethodName(h.getOwner(), h.getName(), h.getDesc()),
+                    mapMethodDesc(h.getDesc()));
+        }
+        return value;
+    }
+
+    /**
+     *
+     * @param typeSignature true if signature is a FieldTypeSignature, such as
+     *        the signature parameter of the ClassVisitor.visitField or
+     *        MethodVisitor.visitLocalVariable methods
+     */
+    public String mapSignature(String signature, boolean typeSignature) {
+        if (signature == null) {
+            return null;
+        }
+        SignatureReader r = new SignatureReader(signature);
+        SignatureWriter w = new SignatureWriter();
+        SignatureVisitor a = createRemappingSignatureAdapter(w);
+        if (typeSignature) {
+            r.acceptType(a);
+        } else {
+            r.accept(a);
+        }
+        return w.toString();
+    }
+
+    protected SignatureVisitor createRemappingSignatureAdapter(
+        SignatureVisitor v)
+    {
+        return new RemappingSignatureAdapter(v, this);
+    }
+
+    /**
+     * Map method name to the new name. Subclasses can override.
+     *
+     * @param owner owner of the method.
+     * @param name name of the method.
+     * @param desc descriptor of the method.
+     * @return new name of the method
+     */
+    public String mapMethodName(String owner, String name, String desc) {
+        return name;
+    }
+
+    /**
+     * Map invokedynamic method name to the new name. Subclasses can override.
+     *
+     * @param name name of the invokedynamic.
+     * @param desc descriptor of the invokedynamic.
+     * @return new invokdynamic name.
+     */
+    public String mapInvokeDynamicMethodName(String name, String desc) {
+        return name;
+    }
+
+    /**
+     * Map field name to the new name. Subclasses can override.
+     *
+     * @param owner owner of the field.
+     * @param name name of the field
+     * @param desc descriptor of the field
+     * @return new name of the field.
+     */
+    public String mapFieldName(String owner, String name, String desc) {
+        return name;
+    }
+
+    /**
+     * Map type name to the new name. Subclasses can override.
+     *
+     */
+    public String map(String typeName) {
+        return typeName;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/RemappingAnnotationAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,115 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * An {@link AnnotationVisitor} adapter for type remapping.
+ *
+ * @author Eugene Kuleshov
+ */
+public class RemappingAnnotationAdapter extends AnnotationVisitor {
+
+    protected final Remapper remapper;
+
+    public RemappingAnnotationAdapter(
+        final AnnotationVisitor av,
+        final Remapper remapper)
+    {
+        this(Opcodes.ASM4, av, remapper);
+    }
+
+    protected RemappingAnnotationAdapter(
+        final int api,
+        final AnnotationVisitor av,
+        final Remapper remapper)
+    {
+        super(api, av);
+        this.remapper = remapper;
+    }
+
+    @Override
+    public void visit(String name, Object value) {
+        av.visit(name, remapper.mapValue(value));
+    }
+
+    @Override
+    public void visitEnum(String name, String desc, String value) {
+        av.visitEnum(name, remapper.mapDesc(desc), value);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(String name, String desc) {
+        AnnotationVisitor v = av.visitAnnotation(name, remapper.mapDesc(desc));
+        return v == null ? null : (v == av
+                ? this
+                : new RemappingAnnotationAdapter(v, remapper));
+    }
+
+    @Override
+    public AnnotationVisitor visitArray(String name) {
+        AnnotationVisitor v = av.visitArray(name);
+        return v == null ? null : (v == av
+                ? this
+                : new RemappingAnnotationAdapter(v, remapper));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/RemappingClassAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,189 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link ClassVisitor} for type remapping.
+ *
+ * @author Eugene Kuleshov
+ */
+public class RemappingClassAdapter extends ClassVisitor {
+
+    protected final Remapper remapper;
+
+    protected String className;
+
+    public RemappingClassAdapter(final ClassVisitor cv, final Remapper remapper)
+    {
+        this(Opcodes.ASM4, cv, remapper);
+    }
+
+    protected RemappingClassAdapter(
+        final int api,
+        final ClassVisitor cv,
+        final Remapper remapper)
+    {
+        super(api, cv);
+        this.remapper = remapper;
+    }
+
+    @Override
+    public void visit(
+        int version,
+        int access,
+        String name,
+        String signature,
+        String superName,
+        String[] interfaces)
+    {
+        this.className = name;
+        super.visit(version,
+                access,
+                remapper.mapType(name),
+                remapper.mapSignature(signature, false),
+                remapper.mapType(superName),
+                interfaces == null ? null
+                        : remapper.mapTypes(interfaces));
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
+        AnnotationVisitor av;
+        av = super.visitAnnotation(remapper.mapDesc(desc), visible);
+        return av == null ? null : createRemappingAnnotationAdapter(av);
+    }
+
+    @Override
+    public FieldVisitor visitField(
+        int access,
+        String name,
+        String desc,
+        String signature,
+        Object value)
+    {
+        FieldVisitor fv = super.visitField(access,
+                remapper.mapFieldName(className, name, desc),
+                remapper.mapDesc(desc),
+                remapper.mapSignature(signature, true),
+                remapper.mapValue(value));
+        return fv == null ? null : createRemappingFieldAdapter(fv);
+    }
+
+    @Override
+    public MethodVisitor visitMethod(
+        int access,
+        String name,
+        String desc,
+        String signature,
+        String[] exceptions)
+    {
+        String newDesc = remapper.mapMethodDesc(desc);
+        MethodVisitor mv = super.visitMethod(access,
+                remapper.mapMethodName(className, name, desc),
+                newDesc,
+                remapper.mapSignature(signature, false),
+                exceptions == null ? null : remapper.mapTypes(exceptions));
+        return mv == null ? null : createRemappingMethodAdapter(access, newDesc, mv);
+    }
+
+    @Override
+    public void visitInnerClass(
+        String name,
+        String outerName,
+        String innerName,
+        int access)
+    {
+        super.visitInnerClass(remapper.mapType(name),
+                outerName == null ? null : remapper.mapType(outerName),
+                innerName, // TODO should it be changed?
+                access);
+    }
+
+    @Override
+    public void visitOuterClass(String owner, String name, String desc) {
+        super.visitOuterClass(remapper.mapType(owner),
+                name == null ? null : remapper.mapMethodName(owner, name, desc),
+                desc == null ? null : remapper.mapMethodDesc(desc));
+    }
+
+    protected FieldVisitor createRemappingFieldAdapter(FieldVisitor fv) {
+        return new RemappingFieldAdapter(fv, remapper);
+    }
+
+    protected MethodVisitor createRemappingMethodAdapter(
+        int access,
+        String newDesc,
+        MethodVisitor mv)
+    {
+        return new RemappingMethodAdapter(access, newDesc, mv, remapper);
+    }
+
+    protected AnnotationVisitor createRemappingAnnotationAdapter(
+        AnnotationVisitor av)
+    {
+        return new RemappingAnnotationAdapter(av, remapper);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/RemappingFieldAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,94 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link FieldVisitor} adapter for type remapping.
+ *
+ * @author Eugene Kuleshov
+ */
+public class RemappingFieldAdapter extends FieldVisitor {
+
+    private final Remapper remapper;
+
+    public RemappingFieldAdapter(final FieldVisitor fv, final Remapper remapper)
+    {
+        this(Opcodes.ASM4, fv, remapper);
+    }
+
+    protected RemappingFieldAdapter(
+        final int api,
+        final FieldVisitor fv,
+        final Remapper remapper)
+    {
+        super(api, fv);
+        this.remapper = remapper;
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
+        AnnotationVisitor av = fv.visitAnnotation(remapper.mapDesc(desc), visible);
+        return av == null ? null : new RemappingAnnotationAdapter(av, remapper);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/RemappingMethodAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,236 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link LocalVariablesSorter} for type mapping.
+ *
+ * @author Eugene Kuleshov
+ */
+public class RemappingMethodAdapter extends LocalVariablesSorter {
+
+    protected final Remapper remapper;
+
+    public RemappingMethodAdapter(
+        final int access,
+        final String desc,
+        final MethodVisitor mv,
+        final Remapper remapper)
+    {
+        this(Opcodes.ASM4, access, desc, mv, remapper);
+    }
+
+    protected RemappingMethodAdapter(
+        final int api,
+        final int access,
+        final String desc,
+        final MethodVisitor mv,
+        final Remapper remapper)
+    {
+        super(api, access, desc, mv);
+        this.remapper = remapper;
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotationDefault() {
+        AnnotationVisitor av = mv.visitAnnotationDefault();
+        return av == null ? av : new RemappingAnnotationAdapter(av, remapper);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(String desc, boolean visible) {
+        AnnotationVisitor av = mv.visitAnnotation(remapper.mapDesc(desc), visible);
+        return av == null ? av : new RemappingAnnotationAdapter(av, remapper);
+    }
+
+    @Override
+    public AnnotationVisitor visitParameterAnnotation(
+        int parameter,
+        String desc,
+        boolean visible)
+    {
+        AnnotationVisitor av = mv.visitParameterAnnotation(parameter,
+                remapper.mapDesc(desc),
+                visible);
+        return av == null ? av : new RemappingAnnotationAdapter(av, remapper);
+    }
+
+    @Override
+    public void visitFrame(
+        int type,
+        int nLocal,
+        Object[] local,
+        int nStack,
+        Object[] stack)
+    {
+        super.visitFrame(type, nLocal, remapEntries(nLocal, local), nStack, remapEntries(nStack, stack));
+    }
+
+    private Object[] remapEntries(int n, Object[] entries) {
+        for (int i = 0; i < n; i++) {
+            if (entries[i] instanceof String) {
+                Object[] newEntries = new Object[n];
+                if (i > 0) {
+                    System.arraycopy(entries, 0, newEntries, 0, i);
+                }
+                do {
+                    Object t = entries[i];
+                    newEntries[i++] = t instanceof String
+                            ? remapper.mapType((String) t)
+                            : t;
+                } while (i < n);
+                return newEntries;
+            }
+        }
+        return entries;
+    }
+
+    @Override
+    public void visitFieldInsn(
+        int opcode,
+        String owner,
+        String name,
+        String desc)
+    {
+        super.visitFieldInsn(opcode,
+                remapper.mapType(owner),
+                remapper.mapFieldName(owner, name, desc),
+                remapper.mapDesc(desc));
+    }
+
+    @Override
+    public void visitMethodInsn(
+        int opcode,
+        String owner,
+        String name,
+        String desc)
+    {
+        super.visitMethodInsn(opcode,
+                remapper.mapType(owner),
+                remapper.mapMethodName(owner, name, desc),
+                remapper.mapMethodDesc(desc));
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        for(int i=0; i<bsmArgs.length; i++) {
+            bsmArgs[i] = remapper.mapValue(bsmArgs[i]);
+        }
+        super.visitInvokeDynamicInsn(
+                remapper.mapInvokeDynamicMethodName(name, desc),
+                remapper.mapMethodDesc(desc),
+                (Handle)remapper.mapValue(bsm),
+                bsmArgs);
+    }
+
+    @Override
+    public void visitTypeInsn(int opcode, String type) {
+        super.visitTypeInsn(opcode, remapper.mapType(type));
+    }
+
+    @Override
+    public void visitLdcInsn(Object cst) {
+        super.visitLdcInsn(remapper.mapValue(cst));
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(String desc, int dims) {
+        super.visitMultiANewArrayInsn(remapper.mapDesc(desc), dims);
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        Label start,
+        Label end,
+        Label handler,
+        String type)
+    {
+        super.visitTryCatchBlock(start, end, handler,
+                type == null ? null : remapper.mapType(type));
+    }
+
+    @Override
+    public void visitLocalVariable(
+        String name,
+        String desc,
+        String signature,
+        Label start,
+        Label end,
+        int index)
+    {
+        super.visitLocalVariable(name,
+                remapper.mapDesc(desc),
+                remapper.mapSignature(signature, true),
+                start,
+                end,
+                index);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/RemappingSignatureAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,187 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.signature.SignatureVisitor;
+
+/**
+ * A {@link SignatureVisitor} adapter for type mapping.
+ *
+ * @author Eugene Kuleshov
+ */
+public class RemappingSignatureAdapter extends SignatureVisitor {
+
+    private final SignatureVisitor v;
+
+    private final Remapper remapper;
+
+    private String className;
+
+    public RemappingSignatureAdapter(
+        final SignatureVisitor v,
+        final Remapper remapper)
+    {
+        this(Opcodes.ASM4, v, remapper);
+    }
+
+    protected RemappingSignatureAdapter(
+        final int api,
+        final SignatureVisitor v,
+        final Remapper remapper)
+    {
+        super(api);
+        this.v = v;
+        this.remapper = remapper;
+    }
+
+    @Override
+    public void visitClassType(String name) {
+        className = name;
+        v.visitClassType(remapper.mapType(name));
+    }
+
+    @Override
+    public void visitInnerClassType(String name) {
+        className = className + '$' + name;
+        String remappedName = remapper.mapType(className);
+        v.visitInnerClassType(remappedName.substring(remappedName.lastIndexOf('$') + 1));
+    }
+
+    @Override
+    public void visitFormalTypeParameter(String name) {
+        v.visitFormalTypeParameter(name);
+    }
+
+    @Override
+    public void visitTypeVariable(String name) {
+        v.visitTypeVariable(name);
+    }
+
+    @Override
+    public SignatureVisitor visitArrayType() {
+        v.visitArrayType();
+        return this;
+    }
+
+    @Override
+    public void visitBaseType(char descriptor) {
+        v.visitBaseType(descriptor);
+    }
+
+    @Override
+    public SignatureVisitor visitClassBound() {
+        v.visitClassBound();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitExceptionType() {
+        v.visitExceptionType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitInterface() {
+        v.visitInterface();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitInterfaceBound() {
+        v.visitInterfaceBound();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitParameterType() {
+        v.visitParameterType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitReturnType() {
+        v.visitReturnType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitSuperclass() {
+        v.visitSuperclass();
+        return this;
+    }
+
+    @Override
+    public void visitTypeArgument() {
+        v.visitTypeArgument();
+    }
+
+    @Override
+    public SignatureVisitor visitTypeArgument(char wildcard) {
+        v.visitTypeArgument(wildcard);
+        return this;
+    }
+
+    @Override
+    public void visitEnd() {
+        v.visitEnd();
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/SerialVersionUIDAdder.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,559 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.io.ByteArrayOutputStream;
+import java.io.DataOutput;
+import java.io.DataOutputStream;
+import java.io.IOException;
+import java.security.MessageDigest;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link ClassVisitor} that adds a serial version unique identifier to a
+ * class if missing. Here is typical usage of this class:
+ *
+ * <pre>
+ *   ClassWriter cw = new ClassWriter(...);
+ *   ClassVisitor sv = new SerialVersionUIDAdder(cw);
+ *   ClassVisitor ca = new MyClassAdapter(sv);
+ *   new ClassReader(orginalClass).accept(ca, false);
+ * </pre>
+ *
+ * The SVUID algorithm can be found <a href=
+ * "http://java.sun.com/j2se/1.4.2/docs/guide/serialization/spec/class.html"
+ * >http://java.sun.com/j2se/1.4.2/docs/guide/serialization/spec/class.html</a>:
+ *
+ * <pre>
+ * The serialVersionUID is computed using the signature of a stream of bytes
+ * that reflect the class definition. The National Institute of Standards and
+ * Technology (NIST) Secure Hash Algorithm (SHA-1) is used to compute a
+ * signature for the stream. The first two 32-bit quantities are used to form a
+ * 64-bit hash. A java.lang.DataOutputStream is used to convert primitive data
+ * types to a sequence of bytes. The values input to the stream are defined by
+ * the Java Virtual Machine (VM) specification for classes.
+ *
+ * The sequence of items in the stream is as follows:
+ *
+ * 1. The class name written using UTF encoding.
+ * 2. The class modifiers written as a 32-bit integer.
+ * 3. The name of each interface sorted by name written using UTF encoding.
+ * 4. For each field of the class sorted by field name (except private static
+ * and private transient fields):
+ * 1. The name of the field in UTF encoding.
+ * 2. The modifiers of the field written as a 32-bit integer.
+ * 3. The descriptor of the field in UTF encoding
+ * 5. If a class initializer exists, write out the following:
+ * 1. The name of the method, &lt;clinit&gt;, in UTF encoding.
+ * 2. The modifier of the method, java.lang.reflect.Modifier.STATIC,
+ * written as a 32-bit integer.
+ * 3. The descriptor of the method, ()V, in UTF encoding.
+ * 6. For each non-private constructor sorted by method name and signature:
+ * 1. The name of the method, &lt;init&gt;, in UTF encoding.
+ * 2. The modifiers of the method written as a 32-bit integer.
+ * 3. The descriptor of the method in UTF encoding.
+ * 7. For each non-private method sorted by method name and signature:
+ * 1. The name of the method in UTF encoding.
+ * 2. The modifiers of the method written as a 32-bit integer.
+ * 3. The descriptor of the method in UTF encoding.
+ * 8. The SHA-1 algorithm is executed on the stream of bytes produced by
+ * DataOutputStream and produces five 32-bit values sha[0..4].
+ *
+ * 9. The hash value is assembled from the first and second 32-bit values of
+ * the SHA-1 message digest. If the result of the message digest, the five
+ * 32-bit words H0 H1 H2 H3 H4, is in an array of five int values named
+ * sha, the hash value would be computed as follows:
+ *
+ * long hash = ((sha[0] &gt;&gt;&gt; 24) &amp; 0xFF) |
+ * ((sha[0] &gt;&gt;&gt; 16) &amp; 0xFF) &lt;&lt; 8 |
+ * ((sha[0] &gt;&gt;&gt; 8) &amp; 0xFF) &lt;&lt; 16 |
+ * ((sha[0] &gt;&gt;&gt; 0) &amp; 0xFF) &lt;&lt; 24 |
+ * ((sha[1] &gt;&gt;&gt; 24) &amp; 0xFF) &lt;&lt; 32 |
+ * ((sha[1] &gt;&gt;&gt; 16) &amp; 0xFF) &lt;&lt; 40 |
+ * ((sha[1] &gt;&gt;&gt; 8) &amp; 0xFF) &lt;&lt; 48 |
+ * ((sha[1] &gt;&gt;&gt; 0) &amp; 0xFF) &lt;&lt; 56;
+ * </pre>
+ *
+ * @author Rajendra Inamdar, Vishal Vishnoi
+ */
+public class SerialVersionUIDAdder extends ClassVisitor {
+
+    /**
+     * Flag that indicates if we need to compute SVUID.
+     */
+    private boolean computeSVUID;
+
+    /**
+     * Set to true if the class already has SVUID.
+     */
+    private boolean hasSVUID;
+
+    /**
+     * Classes access flags.
+     */
+    private int access;
+
+    /**
+     * Internal name of the class
+     */
+    private String name;
+
+    /**
+     * Interfaces implemented by the class.
+     */
+    private String[] interfaces;
+
+    /**
+     * Collection of fields. (except private static and private transient
+     * fields)
+     */
+    private Collection<Item> svuidFields;
+
+    /**
+     * Set to true if the class has static initializer.
+     */
+    private boolean hasStaticInitializer;
+
+    /**
+     * Collection of non-private constructors.
+     */
+    private Collection<Item> svuidConstructors;
+
+    /**
+     * Collection of non-private methods.
+     */
+    private Collection<Item> svuidMethods;
+
+    /**
+     * Creates a new {@link SerialVersionUIDAdder}. <i>Subclasses must not use
+     * this constructor</i>. Instead, they must use the
+     * {@link #SerialVersionUIDAdder(int, ClassVisitor)} version.
+     *
+     * @param cv a {@link ClassVisitor} to which this visitor will delegate
+     *        calls.
+     */
+    public SerialVersionUIDAdder(final ClassVisitor cv) {
+        this(Opcodes.ASM4, cv);
+    }
+
+    /**
+     * Creates a new {@link SerialVersionUIDAdder}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param cv a {@link ClassVisitor} to which this visitor will delegate
+     *        calls.
+     */
+    protected SerialVersionUIDAdder(final int api, final ClassVisitor cv) {
+        super(api, cv);
+        svuidFields = new ArrayList<Item>();
+        svuidConstructors = new ArrayList<Item>();
+        svuidMethods = new ArrayList<Item>();
+    }
+
+    // ------------------------------------------------------------------------
+    // Overriden methods
+    // ------------------------------------------------------------------------
+
+    /*
+     * Visit class header and get class name, access , and interfaces
+     * information (step 1,2, and 3) for SVUID computation.
+     */
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        computeSVUID = (access & Opcodes.ACC_INTERFACE) == 0;
+
+        if (computeSVUID) {
+            this.name = name;
+            this.access = access;
+            this.interfaces = interfaces;
+        }
+
+        super.visit(version, access, name, signature, superName, interfaces);
+    }
+
+    /*
+     * Visit the methods and get constructor and method information (step 5 and
+     * 7). Also determine if there is a class initializer (step 6).
+     */
+    @Override
+    public MethodVisitor visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        if (computeSVUID) {
+            if ("<clinit>".equals(name)) {
+                hasStaticInitializer = true;
+            }
+            /*
+             * Remembers non private constructors and methods for SVUID
+             * computation For constructor and method modifiers, only the
+             * ACC_PUBLIC, ACC_PRIVATE, ACC_PROTECTED, ACC_STATIC, ACC_FINAL,
+             * ACC_SYNCHRONIZED, ACC_NATIVE, ACC_ABSTRACT and ACC_STRICT flags
+             * are used.
+             */
+            int mods = access
+                    & (Opcodes.ACC_PUBLIC | Opcodes.ACC_PRIVATE
+                            | Opcodes.ACC_PROTECTED | Opcodes.ACC_STATIC
+                            | Opcodes.ACC_FINAL | Opcodes.ACC_SYNCHRONIZED
+                            | Opcodes.ACC_NATIVE | Opcodes.ACC_ABSTRACT | Opcodes.ACC_STRICT);
+
+            // all non private methods
+            if ((access & Opcodes.ACC_PRIVATE) == 0) {
+                if ("<init>".equals(name)) {
+                    svuidConstructors.add(new Item(name, mods, desc));
+                } else if (!"<clinit>".equals(name)) {
+                    svuidMethods.add(new Item(name, mods, desc));
+                }
+            }
+        }
+
+        return super.visitMethod(access, name, desc, signature, exceptions);
+    }
+
+    /*
+     * Gets class field information for step 4 of the algorithm. Also determines
+     * if the class already has a SVUID.
+     */
+    @Override
+    public FieldVisitor visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        if (computeSVUID) {
+            if ("serialVersionUID".equals(name)) {
+                // since the class already has SVUID, we won't be computing it.
+                computeSVUID = false;
+                hasSVUID = true;
+            }
+            /*
+             * Remember field for SVUID computation For field modifiers, only
+             * the ACC_PUBLIC, ACC_PRIVATE, ACC_PROTECTED, ACC_STATIC,
+             * ACC_FINAL, ACC_VOLATILE, and ACC_TRANSIENT flags are used when
+             * computing serialVersionUID values.
+             */
+            if ((access & Opcodes.ACC_PRIVATE) == 0
+                    || (access & (Opcodes.ACC_STATIC | Opcodes.ACC_TRANSIENT)) == 0)
+            {
+                int mods = access
+                & (Opcodes.ACC_PUBLIC | Opcodes.ACC_PRIVATE
+                        | Opcodes.ACC_PROTECTED | Opcodes.ACC_STATIC
+                        | Opcodes.ACC_FINAL | Opcodes.ACC_VOLATILE | Opcodes.ACC_TRANSIENT);
+                svuidFields.add(new Item(name, mods, desc));
+            }
+        }
+
+        return super.visitField(access, name, desc, signature, value);
+    }
+
+    /**
+     * Handle a bizarre special case. Nested classes (static classes declared
+     * inside another class) that are protected have their access bit set to
+     * public in their class files to deal with some odd reflection situation.
+     * Our SVUID computation must do as the JVM does and ignore access bits in
+     * the class file in favor of the access bits InnerClass attribute.
+     */
+    @Override
+    public void visitInnerClass(final String aname, final String outerName, final String innerName, final int attr_access) {
+        if ((name != null) && name.equals(aname)) {
+            this.access = attr_access;
+        }
+        super.visitInnerClass(aname, outerName, innerName, attr_access);
+    }
+
+    /*
+     * Add the SVUID if class doesn't have one
+     */
+    @Override
+    public void visitEnd() {
+        // compute SVUID and add it to the class
+        if (computeSVUID && !hasSVUID) {
+            try {
+                super.visitField(Opcodes.ACC_FINAL + Opcodes.ACC_STATIC,
+                        "serialVersionUID",
+                        "J",
+                        null,
+                        new Long(computeSVUID()));
+            } catch (Throwable e) {
+                throw new RuntimeException("Error while computing SVUID for "
+                        + name, e);
+            }
+        }
+
+        super.visitEnd();
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Returns the value of SVUID if the class doesn't have one already. Please
+     * note that 0 is returned if the class already has SVUID, thus use
+     * <code>isHasSVUID</code> to determine if the class already had an SVUID.
+     *
+     * @return Returns the serial version UID
+     * @throws IOException if an I/O error occurs
+     */
+    protected long computeSVUID() throws IOException {
+        ByteArrayOutputStream bos;
+        DataOutputStream dos = null;
+        long svuid = 0;
+
+        try {
+            bos = new ByteArrayOutputStream();
+            dos = new DataOutputStream(bos);
+
+            /*
+             * 1. The class name written using UTF encoding.
+             */
+            dos.writeUTF(name.replace('/', '.'));
+
+            /*
+             * 2. The class modifiers written as a 32-bit integer.
+             */
+            dos.writeInt(access
+                    & (Opcodes.ACC_PUBLIC | Opcodes.ACC_FINAL
+                            | Opcodes.ACC_INTERFACE | Opcodes.ACC_ABSTRACT));
+
+            /*
+             * 3. The name of each interface sorted by name written using UTF
+             * encoding.
+             */
+            Arrays.sort(interfaces);
+            for (int i = 0; i < interfaces.length; i++) {
+                dos.writeUTF(interfaces[i].replace('/', '.'));
+            }
+
+            /*
+             * 4. For each field of the class sorted by field name (except
+             * private static and private transient fields):
+             *
+             * 1. The name of the field in UTF encoding. 2. The modifiers of the
+             * field written as a 32-bit integer. 3. The descriptor of the field
+             * in UTF encoding
+             *
+             * Note that field signatures are not dot separated. Method and
+             * constructor signatures are dot separated. Go figure...
+             */
+            writeItems(svuidFields, dos, false);
+
+            /*
+             * 5. If a class initializer exists, write out the following: 1. The
+             * name of the method, <clinit>, in UTF encoding. 2. The modifier of
+             * the method, java.lang.reflect.Modifier.STATIC, written as a
+             * 32-bit integer. 3. The descriptor of the method, ()V, in UTF
+             * encoding.
+             */
+            if (hasStaticInitializer) {
+                dos.writeUTF("<clinit>");
+                dos.writeInt(Opcodes.ACC_STATIC);
+                dos.writeUTF("()V");
+            } // if..
+
+            /*
+             * 6. For each non-private constructor sorted by method name and
+             * signature: 1. The name of the method, <init>, in UTF encoding. 2.
+             * The modifiers of the method written as a 32-bit integer. 3. The
+             * descriptor of the method in UTF encoding.
+             */
+            writeItems(svuidConstructors, dos, true);
+
+            /*
+             * 7. For each non-private method sorted by method name and
+             * signature: 1. The name of the method in UTF encoding. 2. The
+             * modifiers of the method written as a 32-bit integer. 3. The
+             * descriptor of the method in UTF encoding.
+             */
+            writeItems(svuidMethods, dos, true);
+
+            dos.flush();
+
+            /*
+             * 8. The SHA-1 algorithm is executed on the stream of bytes
+             * produced by DataOutputStream and produces five 32-bit values
+             * sha[0..4].
+             */
+            byte[] hashBytes = computeSHAdigest(bos.toByteArray());
+
+            /*
+             * 9. The hash value is assembled from the first and second 32-bit
+             * values of the SHA-1 message digest. If the result of the message
+             * digest, the five 32-bit words H0 H1 H2 H3 H4, is in an array of
+             * five int values named sha, the hash value would be computed as
+             * follows:
+             *
+             * long hash = ((sha[0] >>> 24) & 0xFF) | ((sha[0] >>> 16) & 0xFF) <<
+             * 8 | ((sha[0] >>> 8) & 0xFF) << 16 | ((sha[0] >>> 0) & 0xFF) <<
+             * 24 | ((sha[1] >>> 24) & 0xFF) << 32 | ((sha[1] >>> 16) & 0xFF) <<
+             * 40 | ((sha[1] >>> 8) & 0xFF) << 48 | ((sha[1] >>> 0) & 0xFF) <<
+             * 56;
+             */
+            for (int i = Math.min(hashBytes.length, 8) - 1; i >= 0; i--) {
+                svuid = (svuid << 8) | (hashBytes[i] & 0xFF);
+            }
+        } finally {
+            // close the stream (if open)
+            if (dos != null) {
+                dos.close();
+            }
+        }
+
+        return svuid;
+    }
+
+    /**
+     * Returns the SHA-1 message digest of the given value.
+     *
+     * @param value the value whose SHA message digest must be computed.
+     * @return the SHA-1 message digest of the given value.
+     */
+    protected byte[] computeSHAdigest(final byte[] value) {
+        try {
+            return MessageDigest.getInstance("SHA").digest(value);
+        } catch (Exception e) {
+            throw new UnsupportedOperationException(e.toString());
+        }
+    }
+
+    /**
+     * Sorts the items in the collection and writes it to the data output stream
+     *
+     * @param itemCollection collection of items
+     * @param dos a <code>DataOutputStream</code> value
+     * @param dotted a <code>boolean</code> value
+     * @exception IOException if an error occurs
+     */
+    private static void writeItems(
+        final Collection<Item> itemCollection,
+        final DataOutput dos,
+        final boolean dotted) throws IOException
+    {
+        int size = itemCollection.size();
+        Item[] items = itemCollection.toArray(new Item[size]);
+        Arrays.sort(items);
+        for (int i = 0; i < size; i++) {
+            dos.writeUTF(items[i].name);
+            dos.writeInt(items[i].access);
+            dos.writeUTF(dotted
+                    ? items[i].desc.replace('/', '.')
+                    : items[i].desc);
+        }
+    }
+
+    // ------------------------------------------------------------------------
+    // Inner classes
+    // ------------------------------------------------------------------------
+
+    private static class Item implements Comparable<Item> {
+
+        final String name;
+
+        final int access;
+
+        final String desc;
+
+        Item(final String name, final int access, final String desc) {
+            this.name = name;
+            this.access = access;
+            this.desc = desc;
+        }
+
+        public int compareTo(final Item other) {
+            int retVal = name.compareTo(other.name);
+            if (retVal == 0) {
+                retVal = desc.compareTo(other.desc);
+            }
+            return retVal;
+        }
+
+        @Override
+        public boolean equals(final Object o) {
+            if (o instanceof Item) {
+                return compareTo((Item) o) == 0;
+            }
+            return false;
+        }
+
+        @Override
+        public int hashCode() {
+            return (name + desc).hashCode();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/SimpleRemapper.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,98 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.Collections;
+import java.util.Map;
+
+/**
+ * A {@link Remapper} using a {@link Map} to define its mapping.
+ *
+ * @author Eugene Kuleshov
+ */
+public class SimpleRemapper extends Remapper {
+
+    private final Map<String, String> mapping;
+
+    public SimpleRemapper(Map<String, String> mapping) {
+        this.mapping = mapping;
+    }
+
+    public SimpleRemapper(String oldName, String newName) {
+        this.mapping = Collections.singletonMap(oldName, newName);
+    }
+
+    @Override
+    public String mapMethodName(String owner, String name, String desc) {
+        String s = map(owner + '.' + name + desc);
+        return s == null ? name : s;
+    }
+
+    @Override
+    public String mapFieldName(String owner, String name, String desc) {
+        String s = map(owner + '.' + name);
+        return s == null ? name : s;
+    }
+
+    @Override
+    public String map(String key) {
+        return mapping.get(key);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/StaticInitMerger.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,138 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link ClassVisitor} that merges clinit methods into a single one.
+ *
+ * @author Eric Bruneton
+ */
+public class StaticInitMerger extends ClassVisitor {
+
+    private String name;
+
+    private MethodVisitor clinit;
+
+    private final String prefix;
+
+    private int counter;
+
+    public StaticInitMerger(final String prefix, final ClassVisitor cv) {
+        this(Opcodes.ASM4, prefix, cv);
+    }
+
+    protected StaticInitMerger(
+        final int api,
+        final String prefix,
+        final ClassVisitor cv)
+    {
+        super(api, cv);
+        this.prefix = prefix;
+    }
+
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        cv.visit(version, access, name, signature, superName, interfaces);
+        this.name = name;
+    }
+
+    @Override
+    public MethodVisitor visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        MethodVisitor mv;
+        if ("<clinit>".equals(name)) {
+            int a = Opcodes.ACC_PRIVATE + Opcodes.ACC_STATIC;
+            String n = prefix + counter++;
+            mv = cv.visitMethod(a, n, desc, signature, exceptions);
+
+            if (clinit == null) {
+                clinit = cv.visitMethod(a, name, desc, null, null);
+            }
+            clinit.visitMethodInsn(Opcodes.INVOKESTATIC, this.name, n, desc);
+        } else {
+            mv = cv.visitMethod(access, name, desc, signature, exceptions);
+        }
+        return mv;
+    }
+
+    @Override
+    public void visitEnd() {
+        if (clinit != null) {
+            clinit.visitInsn(Opcodes.RETURN);
+            clinit.visitMaxs(0, 0);
+        }
+        cv.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/TableSwitchGenerator.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,84 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.commons;
+
+import jdk.internal.org.objectweb.asm.Label;
+
+/**
+ * A code generator for switch statements.
+ *
+ * @author Juozas Baliuka
+ * @author Chris Nokleberg
+ * @author Eric Bruneton
+ */
+public interface TableSwitchGenerator {
+
+    /**
+     * Generates the code for a switch case.
+     *
+     * @param key the switch case key.
+     * @param end a label that corresponds to the end of the switch statement.
+     */
+    void generateCase(int key, Label end);
+
+    /**
+     * Generates the code for the default switch case.
+     */
+    void generateDefault();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/commons/TryCatchBlockSorter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,132 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package jdk.internal.org.objectweb.asm.commons;
+
+import java.util.Collections;
+import java.util.Comparator;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.tree.MethodNode;
+import jdk.internal.org.objectweb.asm.tree.TryCatchBlockNode;
+
+/**
+ * A {@link MethodVisitor} adapter to sort the exception handlers. The handlers
+ * are sorted in a method innermost-to-outermost. This allows the programmer to
+ * add handlers without worrying about ordering them correctly with respect to
+ * existing, in-code handlers.
+ *
+ * Behavior is only defined for properly-nested handlers. If any "try" blocks
+ * overlap (something that isn't possible in Java code) then this may not do
+ * what you want. In fact, this adapter just sorts by the length of the "try"
+ * block, taking advantage of the fact that a given try block must be larger
+ * than any block it contains).
+ *
+ * @author Adrian Sampson
+ */
+public class TryCatchBlockSorter extends MethodNode {
+
+    public TryCatchBlockSorter(
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        this(Opcodes.ASM4, mv, access, name, desc, signature, exceptions);
+    }
+
+    protected TryCatchBlockSorter(
+        final int api,
+        final MethodVisitor mv,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        super(api, access, name, desc, signature, exceptions);
+        this.mv = mv;
+    }
+
+    @Override
+    public void visitEnd() {
+        // Compares TryCatchBlockNodes by the length of their "try" block.
+        Comparator<TryCatchBlockNode> comp = new Comparator<TryCatchBlockNode>() {
+
+            public int compare(TryCatchBlockNode t1, TryCatchBlockNode t2) {
+                int len1 = blockLength(t1);
+                int len2 = blockLength(t2);
+                return len1 - len2;
+            }
+
+            private int blockLength(TryCatchBlockNode block) {
+                int startidx = instructions.indexOf(block.start);
+                int endidx = instructions.indexOf(block.end);
+                return endidx - startidx;
+            }
+        };
+        Collections.sort(tryCatchBlocks, comp);
+        if (mv != null) {
+            accept(mv);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/signature/SignatureReader.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,258 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.signature;
+
+/**
+ * A type signature parser to make a signature visitor visit an existing
+ * signature.
+ *
+ * @author Thomas Hallgren
+ * @author Eric Bruneton
+ */
+public class SignatureReader {
+
+    /**
+     * The signature to be read.
+     */
+    private final String signature;
+
+    /**
+     * Constructs a {@link SignatureReader} for the given signature.
+     *
+     * @param signature A <i>ClassSignature</i>, <i>MethodTypeSignature</i>,
+     *        or <i>FieldTypeSignature</i>.
+     */
+    public SignatureReader(final String signature) {
+        this.signature = signature;
+    }
+
+    /**
+     * Makes the given visitor visit the signature of this
+     * {@link SignatureReader}. This signature is the one specified in the
+     * constructor (see {@link #SignatureReader(String) SignatureReader}). This
+     * method is intended to be called on a {@link SignatureReader} that was
+     * created using a <i>ClassSignature</i> (such as the
+     * <code>signature</code> parameter of the
+     * {@link jdk.internal.org.objectweb.asm.ClassVisitor#visit ClassVisitor.visit} method)
+     * or a <i>MethodTypeSignature</i> (such as the <code>signature</code>
+     * parameter of the
+     * {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitMethod ClassVisitor.visitMethod}
+     * method).
+     *
+     * @param v the visitor that must visit this signature.
+     */
+    public void accept(final SignatureVisitor v) {
+        String signature = this.signature;
+        int len = signature.length();
+        int pos;
+        char c;
+
+        if (signature.charAt(0) == '<') {
+            pos = 2;
+            do {
+                int end = signature.indexOf(':', pos);
+                v.visitFormalTypeParameter(signature.substring(pos - 1, end));
+                pos = end + 1;
+
+                c = signature.charAt(pos);
+                if (c == 'L' || c == '[' || c == 'T') {
+                    pos = parseType(signature, pos, v.visitClassBound());
+                }
+
+                while ((c = signature.charAt(pos++)) == ':') {
+                    pos = parseType(signature, pos, v.visitInterfaceBound());
+                }
+            } while (c != '>');
+        } else {
+            pos = 0;
+        }
+
+        if (signature.charAt(pos) == '(') {
+            pos++;
+            while (signature.charAt(pos) != ')') {
+                pos = parseType(signature, pos, v.visitParameterType());
+            }
+            pos = parseType(signature, pos + 1, v.visitReturnType());
+            while (pos < len) {
+                pos = parseType(signature, pos + 1, v.visitExceptionType());
+            }
+        } else {
+            pos = parseType(signature, pos, v.visitSuperclass());
+            while (pos < len) {
+                pos = parseType(signature, pos, v.visitInterface());
+            }
+        }
+    }
+
+    /**
+     * Makes the given visitor visit the signature of this
+     * {@link SignatureReader}. This signature is the one specified in the
+     * constructor (see {@link #SignatureReader(String) SignatureReader}). This
+     * method is intended to be called on a {@link SignatureReader} that was
+     * created using a <i>FieldTypeSignature</i>, such as the
+     * <code>signature</code> parameter of the
+     * {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitField
+     * ClassVisitor.visitField} or {@link
+     * jdk.internal.org.objectweb.asm.MethodVisitor#visitLocalVariable
+     * MethodVisitor.visitLocalVariable} methods.
+     *
+     * @param v the visitor that must visit this signature.
+     */
+    public void acceptType(final SignatureVisitor v) {
+        parseType(this.signature, 0, v);
+    }
+
+    /**
+     * Parses a field type signature and makes the given visitor visit it.
+     *
+     * @param signature a string containing the signature that must be parsed.
+     * @param pos index of the first character of the signature to parsed.
+     * @param v the visitor that must visit this signature.
+     * @return the index of the first character after the parsed signature.
+     */
+    private static int parseType(
+        final String signature,
+        int pos,
+        final SignatureVisitor v)
+    {
+        char c;
+        int start, end;
+        boolean visited, inner;
+        String name;
+
+        switch (c = signature.charAt(pos++)) {
+            case 'Z':
+            case 'C':
+            case 'B':
+            case 'S':
+            case 'I':
+            case 'F':
+            case 'J':
+            case 'D':
+            case 'V':
+                v.visitBaseType(c);
+                return pos;
+
+            case '[':
+                return parseType(signature, pos, v.visitArrayType());
+
+            case 'T':
+                end = signature.indexOf(';', pos);
+                v.visitTypeVariable(signature.substring(pos, end));
+                return end + 1;
+
+            default: // case 'L':
+                start = pos;
+                visited = false;
+                inner = false;
+                for (;;) {
+                    switch (c = signature.charAt(pos++)) {
+                        case '.':
+                        case ';':
+                            if (!visited) {
+                                name = signature.substring(start, pos - 1);
+                                if (inner) {
+                                    v.visitInnerClassType(name);
+                                } else {
+                                    v.visitClassType(name);
+                                }
+                            }
+                            if (c == ';') {
+                                v.visitEnd();
+                                return pos;
+                            }
+                            start = pos;
+                            visited = false;
+                            inner = true;
+                            break;
+
+                        case '<':
+                            name = signature.substring(start, pos - 1);
+                            if (inner) {
+                                v.visitInnerClassType(name);
+                            } else {
+                                v.visitClassType(name);
+                            }
+                            visited = true;
+                            top: for (;;) {
+                                switch (c = signature.charAt(pos)) {
+                                    case '>':
+                                        break top;
+                                    case '*':
+                                        ++pos;
+                                        v.visitTypeArgument();
+                                        break;
+                                    case '+':
+                                    case '-':
+                                        pos = parseType(signature,
+                                                pos + 1,
+                                                v.visitTypeArgument(c));
+                                        break;
+                                    default:
+                                        pos = parseType(signature,
+                                                pos,
+                                                v.visitTypeArgument('='));
+                                        break;
+                                }
+                            }
+                    }
+                }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/signature/SignatureVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,257 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.signature;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A visitor to visit a generic signature. The methods of this interface must be
+ * called in one of the three following orders (the last one is the only valid
+ * order for a {@link SignatureVisitor} that is returned by a method of this
+ * interface): <ul> <li><i>ClassSignature</i> = (
+ * <tt>visitFormalTypeParameter</tt>
+ *   <tt>visitClassBound</tt>?
+ * <tt>visitInterfaceBound</tt>* )* ( <tt>visitSuperClass</tt>
+ *   <tt>visitInterface</tt>* )</li>
+ * <li><i>MethodSignature</i> = ( <tt>visitFormalTypeParameter</tt>
+ *   <tt>visitClassBound</tt>?
+ * <tt>visitInterfaceBound</tt>* )* ( <tt>visitParameterType</tt>*
+ * <tt>visitReturnType</tt>
+ *   <tt>visitExceptionType</tt>* )</li> <li><i>TypeSignature</i> =
+ * <tt>visitBaseType</tt> | <tt>visitTypeVariable</tt> |
+ * <tt>visitArrayType</tt> | (
+ * <tt>visitClassType</tt> <tt>visitTypeArgument</tt>* (
+ * <tt>visitInnerClassType</tt> <tt>visitTypeArgument</tt>* )*
+ * <tt>visitEnd</tt> ) )</li> </ul>
+ *
+ * @author Thomas Hallgren
+ * @author Eric Bruneton
+ */
+public abstract class SignatureVisitor {
+
+    /**
+     * Wildcard for an "extends" type argument.
+     */
+    public final static char EXTENDS = '+';
+
+    /**
+     * Wildcard for a "super" type argument.
+     */
+    public final static char SUPER = '-';
+
+    /**
+     * Wildcard for a normal type argument.
+     */
+    public final static char INSTANCEOF = '=';
+
+    /**
+     * The ASM API version implemented by this visitor. The value of this field
+     * must be one of {@link Opcodes#ASM4}.
+     */
+    protected final int api;
+
+    /**
+     * Constructs a new {@link SignatureVisitor}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public SignatureVisitor(final int api) {
+        this.api = api;
+    }
+
+    /**
+     * Visits a formal type parameter.
+     *
+     * @param name the name of the formal parameter.
+     */
+    public void visitFormalTypeParameter(String name) {
+    }
+
+    /**
+     * Visits the class bound of the last visited formal type parameter.
+     *
+     * @return a non null visitor to visit the signature of the class bound.
+     */
+    public SignatureVisitor visitClassBound() {
+        return this;
+    }
+
+    /**
+     * Visits an interface bound of the last visited formal type parameter.
+     *
+     * @return a non null visitor to visit the signature of the interface bound.
+     */
+    public SignatureVisitor visitInterfaceBound() {
+        return this;
+    }
+
+    /**
+     * Visits the type of the super class.
+     *
+     * @return a non null visitor to visit the signature of the super class
+     *         type.
+     */
+    public SignatureVisitor visitSuperclass() {
+        return this;
+    }
+
+    /**
+     * Visits the type of an interface implemented by the class.
+     *
+     * @return a non null visitor to visit the signature of the interface type.
+     */
+    public SignatureVisitor visitInterface() {
+        return this;
+    }
+
+    /**
+     * Visits the type of a method parameter.
+     *
+     * @return a non null visitor to visit the signature of the parameter type.
+     */
+    public SignatureVisitor visitParameterType() {
+        return this;
+    }
+
+    /**
+     * Visits the return type of the method.
+     *
+     * @return a non null visitor to visit the signature of the return type.
+     */
+    public SignatureVisitor visitReturnType() {
+        return this;
+    }
+
+    /**
+     * Visits the type of a method exception.
+     *
+     * @return a non null visitor to visit the signature of the exception type.
+     */
+    public SignatureVisitor visitExceptionType() {
+        return this;
+    }
+
+    /**
+     * Visits a signature corresponding to a primitive type.
+     *
+     * @param descriptor the descriptor of the primitive type, or 'V' for
+     *        <tt>void</tt>.
+     */
+    public void visitBaseType(char descriptor) {
+    }
+
+    /**
+     * Visits a signature corresponding to a type variable.
+     *
+     * @param name the name of the type variable.
+     */
+    public void visitTypeVariable(String name) {
+    }
+
+    /**
+     * Visits a signature corresponding to an array type.
+     *
+     * @return a non null visitor to visit the signature of the array element
+     *         type.
+     */
+    public SignatureVisitor visitArrayType() {
+        return this;
+    }
+
+    /**
+     * Starts the visit of a signature corresponding to a class or interface
+     * type.
+     *
+     * @param name the internal name of the class or interface.
+     */
+    public void visitClassType(String name) {
+    }
+
+    /**
+     * Visits an inner class.
+     *
+     * @param name the local name of the inner class in its enclosing class.
+     */
+    public void visitInnerClassType(String name) {
+    }
+
+    /**
+     * Visits an unbounded type argument of the last visited class or inner
+     * class type.
+     */
+    public void visitTypeArgument() {
+    }
+
+    /**
+     * Visits a type argument of the last visited class or inner class type.
+     *
+     * @param wildcard '+', '-' or '='.
+     * @return a non null visitor to visit the signature of the type argument.
+     */
+    public SignatureVisitor visitTypeArgument(char wildcard) {
+        return this;
+    }
+
+    /**
+     * Ends the visit of a signature corresponding to a class or interface type.
+     */
+    public void visitEnd() {
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/signature/SignatureWriter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,256 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.signature;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A signature visitor that generates signatures in string format.
+ *
+ * @author Thomas Hallgren
+ * @author Eric Bruneton
+ */
+public class SignatureWriter extends SignatureVisitor {
+
+    /**
+     * Buffer used to construct the signature.
+     */
+    private final StringBuffer buf = new StringBuffer();
+
+    /**
+     * Indicates if the signature contains formal type parameters.
+     */
+    private boolean hasFormals;
+
+    /**
+     * Indicates if the signature contains method parameter types.
+     */
+    private boolean hasParameters;
+
+    /**
+     * Stack used to keep track of class types that have arguments. Each element
+     * of this stack is a boolean encoded in one bit. The top of the stack is
+     * the lowest order bit. Pushing false = *2, pushing true = *2+1, popping =
+     * /2.
+     */
+    private int argumentStack;
+
+    /**
+     * Constructs a new {@link SignatureWriter} object.
+     */
+    public SignatureWriter() {
+        super(Opcodes.ASM4);
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the SignatureVisitor interface
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visitFormalTypeParameter(final String name) {
+        if (!hasFormals) {
+            hasFormals = true;
+            buf.append('<');
+        }
+        buf.append(name);
+        buf.append(':');
+    }
+
+    @Override
+    public SignatureVisitor visitClassBound() {
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitInterfaceBound() {
+        buf.append(':');
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitSuperclass() {
+        endFormals();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitInterface() {
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitParameterType() {
+        endFormals();
+        if (!hasParameters) {
+            hasParameters = true;
+            buf.append('(');
+        }
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitReturnType() {
+        endFormals();
+        if (!hasParameters) {
+            buf.append('(');
+        }
+        buf.append(')');
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitExceptionType() {
+        buf.append('^');
+        return this;
+    }
+
+    @Override
+    public void visitBaseType(final char descriptor) {
+        buf.append(descriptor);
+    }
+
+    @Override
+    public void visitTypeVariable(final String name) {
+        buf.append('T');
+        buf.append(name);
+        buf.append(';');
+    }
+
+    @Override
+    public SignatureVisitor visitArrayType() {
+        buf.append('[');
+        return this;
+    }
+
+    @Override
+    public void visitClassType(final String name) {
+        buf.append('L');
+        buf.append(name);
+        argumentStack *= 2;
+    }
+
+    @Override
+    public void visitInnerClassType(final String name) {
+        endArguments();
+        buf.append('.');
+        buf.append(name);
+        argumentStack *= 2;
+    }
+
+    @Override
+    public void visitTypeArgument() {
+        if (argumentStack % 2 == 0) {
+            ++argumentStack;
+            buf.append('<');
+        }
+        buf.append('*');
+    }
+
+    @Override
+    public SignatureVisitor visitTypeArgument(final char wildcard) {
+        if (argumentStack % 2 == 0) {
+            ++argumentStack;
+            buf.append('<');
+        }
+        if (wildcard != '=') {
+            buf.append(wildcard);
+        }
+        return this;
+    }
+
+    @Override
+    public void visitEnd() {
+        endArguments();
+        buf.append(';');
+    }
+
+    /**
+     * Returns the signature that was built by this signature writer.
+     *
+     * @return the signature that was built by this signature writer.
+     */
+    @Override
+    public String toString() {
+        return buf.toString();
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Ends the formal type parameters section of the signature.
+     */
+    private void endFormals() {
+        if (hasFormals) {
+            hasFormals = false;
+            buf.append('>');
+        }
+    }
+
+    /**
+     * Ends the type arguments of a class or inner class type.
+     */
+    private void endArguments() {
+        if (argumentStack % 2 != 0) {
+            buf.append('>');
+        }
+        argumentStack /= 2;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/AbstractInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,267 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a bytecode instruction. <i>An instruction can appear
+ * at most once in at most one {@link InsnList} at a time</i>.
+ *
+ * @author Eric Bruneton
+ */
+public abstract class AbstractInsnNode {
+
+    /**
+     * The type of {@link InsnNode} instructions.
+     */
+    public static final int INSN = 0;
+
+    /**
+     * The type of {@link IntInsnNode} instructions.
+     */
+    public static final int INT_INSN = 1;
+
+    /**
+     * The type of {@link VarInsnNode} instructions.
+     */
+    public static final int VAR_INSN = 2;
+
+    /**
+     * The type of {@link TypeInsnNode} instructions.
+     */
+    public static final int TYPE_INSN = 3;
+
+    /**
+     * The type of {@link FieldInsnNode} instructions.
+     */
+    public static final int FIELD_INSN = 4;
+
+    /**
+     * The type of {@link MethodInsnNode} instructions.
+     */
+    public static final int METHOD_INSN = 5;
+
+    /**
+     * The type of {@link InvokeDynamicInsnNode} instructions.
+     */
+    public static final int INVOKE_DYNAMIC_INSN = 6;
+
+    /**
+     * The type of {@link JumpInsnNode} instructions.
+     */
+    public static final int JUMP_INSN = 7;
+
+    /**
+     * The type of {@link LabelNode} "instructions".
+     */
+    public static final int LABEL = 8;
+
+    /**
+     * The type of {@link LdcInsnNode} instructions.
+     */
+    public static final int LDC_INSN = 9;
+
+    /**
+     * The type of {@link IincInsnNode} instructions.
+     */
+    public static final int IINC_INSN = 10;
+
+    /**
+     * The type of {@link TableSwitchInsnNode} instructions.
+     */
+    public static final int TABLESWITCH_INSN = 11;
+
+    /**
+     * The type of {@link LookupSwitchInsnNode} instructions.
+     */
+    public static final int LOOKUPSWITCH_INSN = 12;
+
+    /**
+     * The type of {@link MultiANewArrayInsnNode} instructions.
+     */
+    public static final int MULTIANEWARRAY_INSN = 13;
+
+    /**
+     * The type of {@link FrameNode} "instructions".
+     */
+    public static final int FRAME = 14;
+
+    /**
+     * The type of {@link LineNumberNode} "instructions".
+     */
+    public static final int LINE = 15;
+
+    /**
+     * The opcode of this instruction.
+     */
+    protected int opcode;
+
+    /**
+     * Previous instruction in the list to which this instruction belongs.
+     */
+    AbstractInsnNode prev;
+
+    /**
+     * Next instruction in the list to which this instruction belongs.
+     */
+    AbstractInsnNode next;
+
+    /**
+     * Index of this instruction in the list to which it belongs. The value of
+     * this field is correct only when {@link InsnList#cache} is not null. A
+     * value of -1 indicates that this instruction does not belong to any
+     * {@link InsnList}.
+     */
+    int index;
+
+    /**
+     * Constructs a new {@link AbstractInsnNode}.
+     *
+     * @param opcode the opcode of the instruction to be constructed.
+     */
+    protected AbstractInsnNode(final int opcode) {
+        this.opcode = opcode;
+        this.index = -1;
+    }
+
+    /**
+     * Returns the opcode of this instruction.
+     *
+     * @return the opcode of this instruction.
+     */
+    public int getOpcode() {
+        return opcode;
+    }
+
+    /**
+     * Returns the type of this instruction.
+     *
+     * @return the type of this instruction, i.e. one the constants defined in
+     *         this class.
+     */
+    public abstract int getType();
+
+    /**
+     * Returns the previous instruction in the list to which this instruction
+     * belongs, if any.
+     *
+     * @return the previous instruction in the list to which this instruction
+     *         belongs, if any. May be <tt>null</tt>.
+     */
+    public AbstractInsnNode getPrevious() {
+        return prev;
+    }
+
+    /**
+     * Returns the next instruction in the list to which this instruction
+     * belongs, if any.
+     *
+     * @return the next instruction in the list to which this instruction
+     *         belongs, if any. May be <tt>null</tt>.
+     */
+    public AbstractInsnNode getNext() {
+        return next;
+    }
+
+    /**
+     * Makes the given code visitor visit this instruction.
+     *
+     * @param cv a code visitor.
+     */
+    public abstract void accept(final MethodVisitor cv);
+
+    /**
+     * Returns a copy of this instruction.
+     *
+     * @param labels a map from LabelNodes to cloned LabelNodes.
+     * @return a copy of this instruction. The returned instruction does not
+     *         belong to any {@link InsnList}.
+     */
+    public abstract AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels);
+
+    /**
+     * Returns the clone of the given label.
+     *
+     * @param label a label.
+     * @param map a map from LabelNodes to cloned LabelNodes.
+     * @return the clone of the given label.
+     */
+    static LabelNode clone(final LabelNode label, final Map<LabelNode, LabelNode> map) {
+        return map.get(label);
+    }
+
+    /**
+     * Returns the clones of the given labels.
+     *
+     * @param labels a list of labels.
+     * @param map a map from LabelNodes to cloned LabelNodes.
+     * @return the clones of the given labels.
+     */
+    static LabelNode[] clone(final List<LabelNode> labels, final Map<LabelNode, LabelNode> map) {
+        LabelNode[] clones = new LabelNode[labels.size()];
+        for (int i = 0; i < clones.length; ++i) {
+            clones[i] = map.get(labels.get(i));
+        }
+        return clones;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/AnnotationNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,253 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents an annotationn.
+ *
+ * @author Eric Bruneton
+ */
+public class AnnotationNode extends AnnotationVisitor {
+
+    /**
+     * The class descriptor of the annotation class.
+     */
+    public String desc;
+
+    /**
+     * The name value pairs of this annotation. Each name value pair is stored
+     * as two consecutive elements in the list. The name is a {@link String},
+     * and the value may be a {@link Byte}, {@link Boolean}, {@link Character},
+     * {@link Short}, {@link Integer}, {@link Long}, {@link Float},
+     * {@link Double}, {@link String} or {@link jdk.internal.org.objectweb.asm.Type}, or an
+     * two elements String array (for enumeration values), a
+     * {@link AnnotationNode}, or a {@link List} of values of one of the
+     * preceding types. The list may be <tt>null</tt> if there is no name
+     * value pair.
+     */
+    public List<Object> values;
+
+    /**
+     * Constructs a new {@link AnnotationNode}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #AnnotationNode(int, String)} version.
+     *
+     * @param desc the class descriptor of the annotation class.
+     */
+    public AnnotationNode(final String desc) {
+        this(Opcodes.ASM4, desc);
+    }
+
+    /**
+     * Constructs a new {@link AnnotationNode}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param desc the class descriptor of the annotation class.
+     */
+    public AnnotationNode(final int api, final String desc) {
+        super(api);
+        this.desc = desc;
+    }
+
+    /**
+     * Constructs a new {@link AnnotationNode} to visit an array value.
+     *
+     * @param values where the visited values must be stored.
+     */
+    AnnotationNode(final List<Object> values) {
+        super(Opcodes.ASM4);
+        this.values = values;
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the AnnotationVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(final String name, final Object value) {
+        if (values == null) {
+            values = new ArrayList<Object>(this.desc != null ? 2 : 1);
+        }
+        if (this.desc != null) {
+            values.add(name);
+        }
+        values.add(value);
+    }
+
+    @Override
+    public void visitEnum(
+        final String name,
+        final String desc,
+        final String value)
+    {
+        if (values == null) {
+            values = new ArrayList<Object>(this.desc != null ? 2 : 1);
+        }
+        if (this.desc != null) {
+            values.add(name);
+        }
+        values.add(new String[] { desc, value });
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String name,
+        final String desc)
+    {
+        if (values == null) {
+            values = new ArrayList<Object>(this.desc != null ? 2 : 1);
+        }
+        if (this.desc != null) {
+            values.add(name);
+        }
+        AnnotationNode annotation = new AnnotationNode(desc);
+        values.add(annotation);
+        return annotation;
+    }
+
+    @Override
+    public AnnotationVisitor visitArray(final String name) {
+        if (values == null) {
+            values = new ArrayList<Object>(this.desc != null ? 2 : 1);
+        }
+        if (this.desc != null) {
+            values.add(name);
+        }
+        List<Object> array = new ArrayList<Object>();
+        values.add(array);
+        return new AnnotationNode(array);
+    }
+
+    @Override
+    public void visitEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Accept methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Checks that this annotation node is compatible with the given ASM API
+     * version. This methods checks that this node, and all its nodes
+     * recursively, do not contain elements that were introduced in more recent
+     * versions of the ASM API than the given version.
+     *
+     * @param api an ASM API version. Must be one of {@link Opcodes#ASM4}.
+     */
+    public void check(final int api) {
+        // nothing to do
+    }
+
+    /**
+     * Makes the given visitor visit this annotation.
+     *
+     * @param av an annotation visitor. Maybe <tt>null</tt>.
+     */
+    public void accept(final AnnotationVisitor av) {
+        if (av != null) {
+            if (values != null) {
+                for (int i = 0; i < values.size(); i += 2) {
+                    String name = (String) values.get(i);
+                    Object value = values.get(i + 1);
+                    accept(av, name, value);
+                }
+            }
+            av.visitEnd();
+        }
+    }
+
+    /**
+     * Makes the given visitor visit a given annotation value.
+     *
+     * @param av an annotation visitor. Maybe <tt>null</tt>.
+     * @param name the value name.
+     * @param value the actual value.
+     */
+    static void accept(
+        final AnnotationVisitor av,
+        final String name,
+        final Object value)
+    {
+        if (av != null) {
+            if (value instanceof String[]) {
+                String[] typeconst = (String[]) value;
+                av.visitEnum(name, typeconst[0], typeconst[1]);
+            } else if (value instanceof AnnotationNode) {
+                AnnotationNode an = (AnnotationNode) value;
+                an.accept(av.visitAnnotation(name, an.desc));
+            } else if (value instanceof List) {
+                AnnotationVisitor v = av.visitArray(name);
+                List<?> array = (List<?>) value;
+                for (int j = 0; j < array.size(); ++j) {
+                    accept(v, null, array.get(j));
+                }
+                v.visitEnd();
+            } else {
+                av.visit(name, value);
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/ClassNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,400 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents a class.
+ *
+ * @author Eric Bruneton
+ */
+public class ClassNode extends ClassVisitor {
+
+    /**
+     * The class version.
+     */
+    public int version;
+
+    /**
+     * The class's access flags (see {@link jdk.internal.org.objectweb.asm.Opcodes}). This
+     * field also indicates if the class is deprecated.
+     */
+    public int access;
+
+    /**
+     * The internal name of the class (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     */
+    public String name;
+
+    /**
+     * The signature of the class. Mayt be <tt>null</tt>.
+     */
+    public String signature;
+
+    /**
+     * The internal of name of the super class (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}). For
+     * interfaces, the super class is {@link Object}. May be <tt>null</tt>,
+     * but only for the {@link Object} class.
+     */
+    public String superName;
+
+    /**
+     * The internal names of the class's interfaces (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}). This
+     * list is a list of {@link String} objects.
+     */
+    public List<String> interfaces;
+
+    /**
+     * The name of the source file from which this class was compiled. May be
+     * <tt>null</tt>.
+     */
+    public String sourceFile;
+
+    /**
+     * Debug information to compute the correspondance between source and
+     * compiled elements of the class. May be <tt>null</tt>.
+     */
+    public String sourceDebug;
+
+    /**
+     * The internal name of the enclosing class of the class. May be
+     * <tt>null</tt>.
+     */
+    public String outerClass;
+
+    /**
+     * The name of the method that contains the class, or <tt>null</tt> if the
+     * class is not enclosed in a method.
+     */
+    public String outerMethod;
+
+    /**
+     * The descriptor of the method that contains the class, or <tt>null</tt>
+     * if the class is not enclosed in a method.
+     */
+    public String outerMethodDesc;
+
+    /**
+     * The runtime visible annotations of this class. This list is a list of
+     * {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label visible
+     */
+    public List<AnnotationNode> visibleAnnotations;
+
+    /**
+     * The runtime invisible annotations of this class. This list is a list of
+     * {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label invisible
+     */
+    public List<AnnotationNode> invisibleAnnotations;
+
+    /**
+     * The non standard attributes of this class. This list is a list of
+     * {@link Attribute} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.Attribute
+     */
+    public List<Attribute> attrs;
+
+    /**
+     * Informations about the inner classes of this class. This list is a list
+     * of {@link InnerClassNode} objects.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.InnerClassNode
+     */
+    public List<InnerClassNode> innerClasses;
+
+    /**
+     * The fields of this class. This list is a list of {@link FieldNode}
+     * objects.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.FieldNode
+     */
+    public List<FieldNode> fields;
+
+    /**
+     * The methods of this class. This list is a list of {@link MethodNode}
+     * objects.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.MethodNode
+     */
+    public List<MethodNode> methods;
+
+    /**
+     * Constructs a new {@link ClassNode}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the {@link #ClassNode(int)}
+     * version.
+     */
+    public ClassNode() {
+        this(Opcodes.ASM4);
+    }
+
+    /**
+     * Constructs a new {@link ClassNode}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public ClassNode(final int api) {
+        super(api);
+        this.interfaces = new ArrayList<String>();
+        this.innerClasses = new ArrayList<InnerClassNode>();
+        this.fields = new ArrayList<FieldNode>();
+        this.methods = new ArrayList<MethodNode>();
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the ClassVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        this.version = version;
+        this.access = access;
+        this.name = name;
+        this.signature = signature;
+        this.superName = superName;
+        if (interfaces != null) {
+            this.interfaces.addAll(Arrays.asList(interfaces));
+        }
+    }
+
+    @Override
+    public void visitSource(final String file, final String debug) {
+        sourceFile = file;
+        sourceDebug = debug;
+    }
+
+    @Override
+    public void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        outerClass = owner;
+        outerMethod = name;
+        outerMethodDesc = desc;
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        AnnotationNode an = new AnnotationNode(desc);
+        if (visible) {
+            if (visibleAnnotations == null) {
+                visibleAnnotations = new ArrayList<AnnotationNode>(1);
+            }
+            visibleAnnotations.add(an);
+        } else {
+            if (invisibleAnnotations == null) {
+                invisibleAnnotations = new ArrayList<AnnotationNode>(1);
+            }
+            invisibleAnnotations.add(an);
+        }
+        return an;
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        if (attrs == null) {
+            attrs = new ArrayList<Attribute>(1);
+        }
+        attrs.add(attr);
+    }
+
+    @Override
+    public void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        InnerClassNode icn = new InnerClassNode(name,
+                outerName,
+                innerName,
+                access);
+        innerClasses.add(icn);
+    }
+
+    @Override
+    public FieldVisitor visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        FieldNode fn = new FieldNode(access, name, desc, signature, value);
+        fields.add(fn);
+        return fn;
+    }
+
+    @Override
+    public MethodVisitor visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        MethodNode mn = new MethodNode(access,
+                name,
+                desc,
+                signature,
+                exceptions);
+        methods.add(mn);
+        return mn;
+    }
+
+    @Override
+    public void visitEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Accept method
+    // ------------------------------------------------------------------------
+
+    /**
+     * Checks that this class node is compatible with the given ASM API version.
+     * This methods checks that this node, and all its nodes recursively, do not
+     * contain elements that were introduced in more recent versions of the ASM
+     * API than the given version.
+     *
+     * @param api an ASM API version. Must be one of {@link Opcodes#ASM4}.
+     */
+    public void check(final int api) {
+        // nothing to do
+    }
+
+    /**
+     * Makes the given class visitor visit this class.
+     *
+     * @param cv a class visitor.
+     */
+    public void accept(final ClassVisitor cv) {
+        // visits header
+        String[] interfaces = new String[this.interfaces.size()];
+        this.interfaces.toArray(interfaces);
+        cv.visit(version, access, name, signature, superName, interfaces);
+        // visits source
+        if (sourceFile != null || sourceDebug != null) {
+            cv.visitSource(sourceFile, sourceDebug);
+        }
+        // visits outer class
+        if (outerClass != null) {
+            cv.visitOuterClass(outerClass, outerMethod, outerMethodDesc);
+        }
+        // visits attributes
+        int i, n;
+        n = visibleAnnotations == null ? 0 : visibleAnnotations.size();
+        for (i = 0; i < n; ++i) {
+            AnnotationNode an = visibleAnnotations.get(i);
+            an.accept(cv.visitAnnotation(an.desc, true));
+        }
+        n = invisibleAnnotations == null ? 0 : invisibleAnnotations.size();
+        for (i = 0; i < n; ++i) {
+            AnnotationNode an = invisibleAnnotations.get(i);
+            an.accept(cv.visitAnnotation(an.desc, false));
+        }
+        n = attrs == null ? 0 : attrs.size();
+        for (i = 0; i < n; ++i) {
+            cv.visitAttribute(attrs.get(i));
+        }
+        // visits inner classes
+        for (i = 0; i < innerClasses.size(); ++i) {
+            innerClasses.get(i).accept(cv);
+        }
+        // visits fields
+        for (i = 0; i < fields.size(); ++i) {
+            fields.get(i).accept(cv);
+        }
+        // visits methods
+        for (i = 0; i < methods.size(); ++i) {
+            methods.get(i).accept(cv);
+        }
+        // visits end
+        cv.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/FieldInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,135 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a field instruction. A field instruction is an
+ * instruction that loads or stores the value of a field of an object.
+ *
+ * @author Eric Bruneton
+ */
+public class FieldInsnNode extends AbstractInsnNode {
+
+    /**
+     * The internal name of the field's owner class (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     */
+    public String owner;
+
+    /**
+     * The field's name.
+     */
+    public String name;
+
+    /**
+     * The field's descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public String desc;
+
+    /**
+     * Constructs a new {@link FieldInsnNode}.
+     *
+     * @param opcode the opcode of the type instruction to be constructed. This
+     *        opcode must be GETSTATIC, PUTSTATIC, GETFIELD or PUTFIELD.
+     * @param owner the internal name of the field's owner class (see
+     *        {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     * @param name the field's name.
+     * @param desc the field's descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public FieldInsnNode(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        super(opcode);
+        this.owner = owner;
+        this.name = name;
+        this.desc = desc;
+    }
+
+    /**
+     * Sets the opcode of this instruction.
+     *
+     * @param opcode the new instruction opcode. This opcode must be GETSTATIC,
+     *        PUTSTATIC, GETFIELD or PUTFIELD.
+     */
+    public void setOpcode(final int opcode) {
+        this.opcode = opcode;
+    }
+
+    @Override
+    public int getType() {
+        return FIELD_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor cv) {
+        cv.visitFieldInsn(opcode, owner, name, desc);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new FieldInsnNode(opcode, owner, name, desc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/FieldNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,272 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents a field.
+ *
+ * @author Eric Bruneton
+ */
+public class FieldNode extends FieldVisitor {
+
+    /**
+     * The field's access flags (see {@link jdk.internal.org.objectweb.asm.Opcodes}). This
+     * field also indicates if the field is synthetic and/or deprecated.
+     */
+    public int access;
+
+    /**
+     * The field's name.
+     */
+    public String name;
+
+    /**
+     * The field's descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public String desc;
+
+    /**
+     * The field's signature. May be <tt>null</tt>.
+     */
+    public String signature;
+
+    /**
+     * The field's initial value. This field, which may be <tt>null</tt> if
+     * the field does not have an initial value, must be an {@link Integer}, a
+     * {@link Float}, a {@link Long}, a {@link Double} or a {@link String}.
+     */
+    public Object value;
+
+    /**
+     * The runtime visible annotations of this field. This list is a list of
+     * {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label visible
+     */
+    public List<AnnotationNode> visibleAnnotations;
+
+    /**
+     * The runtime invisible annotations of this field. This list is a list of
+     * {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label invisible
+     */
+    public List<AnnotationNode> invisibleAnnotations;
+
+    /**
+     * The non standard attributes of this field. This list is a list of
+     * {@link Attribute} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.Attribute
+     */
+    public List<Attribute> attrs;
+
+    /**
+     * Constructs a new {@link FieldNode}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #FieldNode(int, int, String, String, String, Object)} version.
+     *
+     * @param access the field's access flags (see
+     *        {@link jdk.internal.org.objectweb.asm.Opcodes}). This parameter also indicates
+     *        if the field is synthetic and/or deprecated.
+     * @param name the field's name.
+     * @param desc the field's descriptor (see {@link jdk.internal.org.objectweb.asm.Type
+     *        Type}).
+     * @param signature the field's signature.
+     * @param value the field's initial value. This parameter, which may be
+     *        <tt>null</tt> if the field does not have an initial value, must be
+     *        an {@link Integer}, a {@link Float}, a {@link Long}, a
+     *        {@link Double} or a {@link String}.
+     */
+    public FieldNode(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        this(Opcodes.ASM4, access, name, desc, signature, value);
+    }
+
+    /**
+     * Constructs a new {@link FieldNode}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #FieldNode(int, int, String, String, String, Object)} version.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param access the field's access flags (see
+     *        {@link jdk.internal.org.objectweb.asm.Opcodes}). This parameter also indicates
+     *        if the field is synthetic and/or deprecated.
+     * @param name the field's name.
+     * @param desc the field's descriptor (see {@link jdk.internal.org.objectweb.asm.Type
+     *        Type}).
+     * @param signature the field's signature.
+     * @param value the field's initial value. This parameter, which may be
+     *        <tt>null</tt> if the field does not have an initial value, must be
+     *        an {@link Integer}, a {@link Float}, a {@link Long}, a
+     *        {@link Double} or a {@link String}.
+     */
+    public FieldNode(
+        final int api,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        super(api);
+        this.access = access;
+        this.name = name;
+        this.desc = desc;
+        this.signature = signature;
+        this.value = value;
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the FieldVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        AnnotationNode an = new AnnotationNode(desc);
+        if (visible) {
+            if (visibleAnnotations == null) {
+                visibleAnnotations = new ArrayList<AnnotationNode>(1);
+            }
+            visibleAnnotations.add(an);
+        } else {
+            if (invisibleAnnotations == null) {
+                invisibleAnnotations = new ArrayList<AnnotationNode>(1);
+            }
+            invisibleAnnotations.add(an);
+        }
+        return an;
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        if (attrs == null) {
+            attrs = new ArrayList<Attribute>(1);
+        }
+        attrs.add(attr);
+    }
+
+    @Override
+    public void visitEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Accept methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Checks that this field node is compatible with the given ASM API version.
+     * This methods checks that this node, and all its nodes recursively, do not
+     * contain elements that were introduced in more recent versions of the ASM
+     * API than the given version.
+     *
+     * @param api an ASM API version. Must be one of {@link Opcodes#ASM4}.
+     */
+    public void check(final int api) {
+        // nothing to do
+    }
+
+    /**
+     * Makes the given class visitor visit this field.
+     *
+     * @param cv a class visitor.
+     */
+    public void accept(final ClassVisitor cv) {
+        FieldVisitor fv = cv.visitField(access, name, desc, signature, value);
+        if (fv == null) {
+            return;
+        }
+        int i, n;
+        n = visibleAnnotations == null ? 0 : visibleAnnotations.size();
+        for (i = 0; i < n; ++i) {
+            AnnotationNode an = visibleAnnotations.get(i);
+            an.accept(fv.visitAnnotation(an.desc, true));
+        }
+        n = invisibleAnnotations == null ? 0 : invisibleAnnotations.size();
+        for (i = 0; i < n; ++i) {
+            AnnotationNode an = invisibleAnnotations.get(i);
+            an.accept(fv.visitAnnotation(an.desc, false));
+        }
+        n = attrs == null ? 0 : attrs.size();
+        for (i = 0; i < n; ++i) {
+            fv.visitAttribute(attrs.get(i));
+        }
+        fv.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/FrameNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,240 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents a stack map frame. These nodes are pseudo instruction
+ * nodes in order to be inserted in an instruction list. In fact these nodes
+ * must(*) be inserted <i>just before</i> any instruction node <b>i</b> that
+ * follows an unconditionnal branch instruction such as GOTO or THROW, that is
+ * the target of a jump instruction, or that starts an exception handler block.
+ * The stack map frame types must describe the values of the local variables and
+ * of the operand stack elements <i>just before</i> <b>i</b> is executed. <br>
+ * <br> (*) this is mandatory only for classes whose version is greater than or
+ * equal to {@link Opcodes#V1_6 V1_6}.
+ *
+ * @author Eric Bruneton
+ */
+public class FrameNode extends AbstractInsnNode {
+
+    /**
+     * The type of this frame. Must be {@link Opcodes#F_NEW} for expanded
+     * frames, or {@link Opcodes#F_FULL}, {@link Opcodes#F_APPEND},
+     * {@link Opcodes#F_CHOP}, {@link Opcodes#F_SAME} or
+     * {@link Opcodes#F_APPEND}, {@link Opcodes#F_SAME1} for compressed frames.
+     */
+    public int type;
+
+    /**
+     * The types of the local variables of this stack map frame. Elements of
+     * this list can be Integer, String or LabelNode objects (for primitive,
+     * reference and uninitialized types respectively - see
+     * {@link MethodVisitor}).
+     */
+    public List<Object> local;
+
+    /**
+     * The types of the operand stack elements of this stack map frame. Elements
+     * of this list can be Integer, String or LabelNode objects (for primitive,
+     * reference and uninitialized types respectively - see
+     * {@link MethodVisitor}).
+     */
+    public List<Object> stack;
+
+    private FrameNode() {
+        super(-1);
+    }
+
+    /**
+     * Constructs a new {@link FrameNode}.
+     *
+     * @param type the type of this frame. Must be {@link Opcodes#F_NEW} for
+     *        expanded frames, or {@link Opcodes#F_FULL},
+     *        {@link Opcodes#F_APPEND}, {@link Opcodes#F_CHOP},
+     *        {@link Opcodes#F_SAME} or {@link Opcodes#F_APPEND},
+     *        {@link Opcodes#F_SAME1} for compressed frames.
+     * @param nLocal number of local variables of this stack map frame.
+     * @param local the types of the local variables of this stack map frame.
+     *        Elements of this list can be Integer, String or LabelNode objects
+     *        (for primitive, reference and uninitialized types respectively -
+     *        see {@link MethodVisitor}).
+     * @param nStack number of operand stack elements of this stack map frame.
+     * @param stack the types of the operand stack elements of this stack map
+     *        frame. Elements of this list can be Integer, String or LabelNode
+     *        objects (for primitive, reference and uninitialized types
+     *        respectively - see {@link MethodVisitor}).
+     */
+    public FrameNode(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        super(-1);
+        this.type = type;
+        switch (type) {
+            case Opcodes.F_NEW:
+            case Opcodes.F_FULL:
+                this.local = asList(nLocal, local);
+                this.stack = asList(nStack, stack);
+                break;
+            case Opcodes.F_APPEND:
+                this.local = asList(nLocal, local);
+                break;
+            case Opcodes.F_CHOP:
+                this.local = Arrays.asList(new Object[nLocal]);
+                break;
+            case Opcodes.F_SAME:
+                break;
+            case Opcodes.F_SAME1:
+                this.stack = asList(1, stack);
+                break;
+        }
+    }
+
+    @Override
+    public int getType() {
+        return FRAME;
+    }
+
+    /**
+     * Makes the given visitor visit this stack map frame.
+     *
+     * @param mv a method visitor.
+     */
+    @Override
+    public void accept(final MethodVisitor mv) {
+        switch (type) {
+            case Opcodes.F_NEW:
+            case Opcodes.F_FULL:
+                mv.visitFrame(type,
+                        local.size(),
+                        asArray(local),
+                        stack.size(),
+                        asArray(stack));
+                break;
+            case Opcodes.F_APPEND:
+                mv.visitFrame(type, local.size(), asArray(local), 0, null);
+                break;
+            case Opcodes.F_CHOP:
+                mv.visitFrame(type, local.size(), null, 0, null);
+                break;
+            case Opcodes.F_SAME:
+                mv.visitFrame(type, 0, null, 0, null);
+                break;
+            case Opcodes.F_SAME1:
+                mv.visitFrame(type, 0, null, 1, asArray(stack));
+                break;
+        }
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        FrameNode clone = new FrameNode();
+        clone.type = type;
+        if (local != null) {
+            clone.local = new ArrayList<Object>();
+            for (int i = 0; i < local.size(); ++i) {
+                Object l = local.get(i);
+                if (l instanceof LabelNode) {
+                    l = labels.get(l);
+                }
+                clone.local.add(l);
+            }
+        }
+        if (stack != null) {
+            clone.stack = new ArrayList<Object>();
+            for (int i = 0; i < stack.size(); ++i) {
+                Object s = stack.get(i);
+                if (s instanceof LabelNode) {
+                    s = labels.get(s);
+                }
+                clone.stack.add(s);
+            }
+        }
+        return clone;
+    }
+
+    // ------------------------------------------------------------------------
+
+    private static List<Object> asList(final int n, final Object[] o) {
+        return Arrays.asList(o).subList(0, n);
+    }
+
+    private static Object[] asArray(final List<Object> l) {
+        Object[] objs = new Object[l.size()];
+        for (int i = 0; i < objs.length; ++i) {
+            Object o = l.get(i);
+            if (o instanceof LabelNode) {
+                o = ((LabelNode) o).getLabel();
+            }
+            objs[i] = o;
+        }
+        return objs;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/IincInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,109 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents an IINC instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class IincInsnNode extends AbstractInsnNode {
+
+    /**
+     * Index of the local variable to be incremented.
+     */
+    public int var;
+
+    /**
+     * Amount to increment the local variable by.
+     */
+    public int incr;
+
+    /**
+     * Constructs a new {@link IincInsnNode}.
+     *
+     * @param var index of the local variable to be incremented.
+     * @param incr increment amount to increment the local variable by.
+     */
+    public IincInsnNode(final int var, final int incr) {
+        super(Opcodes.IINC);
+        this.var = var;
+        this.incr = incr;
+    }
+
+    @Override
+    public int getType() {
+        return IINC_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitIincInsn(var, incr);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new IincInsnNode(var, incr);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/InnerClassNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,130 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+
+/**
+ * A node that represents an inner class.
+ *
+ * @author Eric Bruneton
+ */
+public class InnerClassNode {
+
+    /**
+     * The internal name of an inner class (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     */
+    public String name;
+
+    /**
+     * The internal name of the class to which the inner class belongs (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}). May
+     * be <tt>null</tt>.
+     */
+    public String outerName;
+
+    /**
+     * The (simple) name of the inner class inside its enclosing class. May be
+     * <tt>null</tt> for anonymous inner classes.
+     */
+    public String innerName;
+
+    /**
+     * The access flags of the inner class as originally declared in the
+     * enclosing class.
+     */
+    public int access;
+
+    /**
+     * Constructs a new {@link InnerClassNode}.
+     *
+     * @param name the internal name of an inner class (see
+     *        {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     * @param outerName the internal name of the class to which the inner class
+     *        belongs (see
+     *        {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     *        May be <tt>null</tt>.
+     * @param innerName the (simple) name of the inner class inside its
+     *        enclosing class. May be <tt>null</tt> for anonymous inner
+     *        classes.
+     * @param access the access flags of the inner class as originally declared
+     *        in the enclosing class.
+     */
+    public InnerClassNode(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        this.name = name;
+        this.outerName = outerName;
+        this.innerName = innerName;
+        this.access = access;
+    }
+
+    /**
+     * Makes the given class visitor visit this inner class.
+     *
+     * @param cv a class visitor.
+     */
+    public void accept(final ClassVisitor cv) {
+        cv.visitInnerClass(name, outerName, innerName, access);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/InsnList.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,607 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ListIterator;
+import java.util.NoSuchElementException;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A doubly linked list of {@link AbstractInsnNode} objects. <i>This
+ * implementation is not thread safe</i>.
+ */
+public class InsnList {
+
+    /**
+     * The number of instructions in this list.
+     */
+    private int size;
+
+    /**
+     * The first instruction in this list. May be <tt>null</tt>.
+     */
+    private AbstractInsnNode first;
+
+    /**
+     * The last instruction in this list. May be <tt>null</tt>.
+     */
+    private AbstractInsnNode last;
+
+    /**
+     * A cache of the instructions of this list. This cache is used to improve
+     * the performance of the {@link #get} method.
+     */
+    AbstractInsnNode[] cache;
+
+    /**
+     * Returns the number of instructions in this list.
+     *
+     * @return the number of instructions in this list.
+     */
+    public int size() {
+        return size;
+    }
+
+    /**
+     * Returns the first instruction in this list.
+     *
+     * @return the first instruction in this list, or <tt>null</tt> if the
+     *         list is empty.
+     */
+    public AbstractInsnNode getFirst() {
+        return first;
+    }
+
+    /**
+     * Returns the last instruction in this list.
+     *
+     * @return the last instruction in this list, or <tt>null</tt> if the list
+     *         is empty.
+     */
+    public AbstractInsnNode getLast() {
+        return last;
+    }
+
+    /**
+     * Returns the instruction whose index is given. This method builds a cache
+     * of the instructions in this list to avoid scanning the whole list each
+     * time it is called. Once the cache is built, this method run in constant
+     * time. This cache is invalidated by all the methods that modify the list.
+     *
+     * @param index the index of the instruction that must be returned.
+     * @return the instruction whose index is given.
+     * @throws IndexOutOfBoundsException if (index < 0 || index >= size()).
+     */
+    public AbstractInsnNode get(final int index) {
+        if (index < 0 || index >= size) {
+            throw new IndexOutOfBoundsException();
+        }
+        if (cache == null) {
+            cache = toArray();
+        }
+        return cache[index];
+    }
+
+    /**
+     * Returns <tt>true</tt> if the given instruction belongs to this list.
+     * This method always scans the instructions of this list until it finds the
+     * given instruction or reaches the end of the list.
+     *
+     * @param insn an instruction.
+     * @return <tt>true</tt> if the given instruction belongs to this list.
+     */
+    public boolean contains(final AbstractInsnNode insn) {
+        AbstractInsnNode i = first;
+        while (i != null && i != insn) {
+            i = i.next;
+        }
+        return i != null;
+    }
+
+    /**
+     * Returns the index of the given instruction in this list. This method
+     * builds a cache of the instruction indexes to avoid scanning the whole
+     * list each time it is called. Once the cache is built, this method run in
+     * constant time. The cache is invalidated by all the methods that modify
+     * the list.
+     *
+     * @param insn an instruction <i>of this list</i>.
+     * @return the index of the given instruction in this list. <i>The result of
+     *         this method is undefined if the given instruction does not belong
+     *         to this list</i>. Use {@link #contains contains} to test if an
+     *         instruction belongs to an instruction list or not.
+     */
+    public int indexOf(final AbstractInsnNode insn) {
+        if (cache == null) {
+            cache = toArray();
+        }
+        return insn.index;
+    }
+
+    /**
+     * Makes the given visitor visit all of the instructions in this list.
+     *
+     * @param mv the method visitor that must visit the instructions.
+     */
+    public void accept(final MethodVisitor mv) {
+        AbstractInsnNode insn = first;
+        while (insn != null) {
+            insn.accept(mv);
+            insn = insn.next;
+        }
+    }
+
+    /**
+     * Returns an iterator over the instructions in this list.
+     *
+     * @return an iterator over the instructions in this list.
+     */
+    public ListIterator<AbstractInsnNode> iterator() {
+        return iterator(0);
+    }
+
+    /**
+     * Returns an iterator over the instructions in this list.
+     *
+     * @return an iterator over the instructions in this list.
+     */
+    @SuppressWarnings("unchecked")
+    public ListIterator<AbstractInsnNode> iterator(int index) {
+        return new InsnListIterator(index);
+    }
+
+    /**
+     * Returns an array containing all of the instructions in this list.
+     *
+     * @return an array containing all of the instructions in this list.
+     */
+    public AbstractInsnNode[] toArray() {
+        int i = 0;
+        AbstractInsnNode elem = first;
+        AbstractInsnNode[] insns = new AbstractInsnNode[size];
+        while (elem != null) {
+            insns[i] = elem;
+            elem.index = i++;
+            elem = elem.next;
+        }
+        return insns;
+    }
+
+    /**
+     * Replaces an instruction of this list with another instruction.
+     *
+     * @param location an instruction <i>of this list</i>.
+     * @param insn another instruction, <i>which must not belong to any
+     *        {@link InsnList}</i>.
+     */
+    public void set(final AbstractInsnNode location, final AbstractInsnNode insn) {
+        AbstractInsnNode next = location.next;
+        insn.next = next;
+        if (next != null) {
+            next.prev = insn;
+        } else {
+            last = insn;
+        }
+        AbstractInsnNode prev = location.prev;
+        insn.prev = prev;
+        if (prev != null) {
+            prev.next = insn;
+        } else {
+            first = insn;
+        }
+        if (cache != null) {
+            int index = location.index;
+            cache[index] = insn;
+            insn.index = index;
+        } else {
+            insn.index = 0; // insn now belongs to an InsnList
+        }
+        location.index = -1; // i no longer belongs to an InsnList
+        location.prev = null;
+        location.next = null;
+    }
+
+    /**
+     * Adds the given instruction to the end of this list.
+     *
+     * @param insn an instruction, <i>which must not belong to any
+     *        {@link InsnList}</i>.
+     */
+    public void add(final AbstractInsnNode insn) {
+        ++size;
+        if (last == null) {
+            first = insn;
+            last = insn;
+        } else {
+            last.next = insn;
+            insn.prev = last;
+        }
+        last = insn;
+        cache = null;
+        insn.index = 0; // insn now belongs to an InsnList
+    }
+
+    /**
+     * Adds the given instructions to the end of this list.
+     *
+     * @param insns an instruction list, which is cleared during the process.
+     *        This list must be different from 'this'.
+     */
+    public void add(final InsnList insns) {
+        if (insns.size == 0) {
+            return;
+        }
+        size += insns.size;
+        if (last == null) {
+            first = insns.first;
+            last = insns.last;
+        } else {
+            AbstractInsnNode elem = insns.first;
+            last.next = elem;
+            elem.prev = last;
+            last = insns.last;
+        }
+        cache = null;
+        insns.removeAll(false);
+    }
+
+    /**
+     * Inserts the given instruction at the begining of this list.
+     *
+     * @param insn an instruction, <i>which must not belong to any
+     *        {@link InsnList}</i>.
+     */
+    public void insert(final AbstractInsnNode insn) {
+        ++size;
+        if (first == null) {
+            first = insn;
+            last = insn;
+        } else {
+            first.prev = insn;
+            insn.next = first;
+        }
+        first = insn;
+        cache = null;
+        insn.index = 0; // insn now belongs to an InsnList
+    }
+
+    /**
+     * Inserts the given instructions at the begining of this list.
+     *
+     * @param insns an instruction list, which is cleared during the process.
+     *        This list must be different from 'this'.
+     */
+    public void insert(final InsnList insns) {
+        if (insns.size == 0) {
+            return;
+        }
+        size += insns.size;
+        if (first == null) {
+            first = insns.first;
+            last = insns.last;
+        } else {
+            AbstractInsnNode elem = insns.last;
+            first.prev = elem;
+            elem.next = first;
+            first = insns.first;
+        }
+        cache = null;
+        insns.removeAll(false);
+    }
+
+    /**
+     * Inserts the given instruction after the specified instruction.
+     *
+     * @param location an instruction <i>of this list</i> after which insn must be
+     *        inserted.
+     * @param insn the instruction to be inserted, <i>which must not belong to
+     *        any {@link InsnList}</i>.
+     */
+    public void insert(final AbstractInsnNode location, final AbstractInsnNode insn) {
+        ++size;
+        AbstractInsnNode next = location.next;
+        if (next == null) {
+            last = insn;
+        } else {
+            next.prev = insn;
+        }
+        location.next = insn;
+        insn.next = next;
+        insn.prev = location;
+        cache = null;
+        insn.index = 0; // insn now belongs to an InsnList
+    }
+
+    /**
+     * Inserts the given instructions after the specified instruction.
+     *
+     * @param location an instruction <i>of this list</i> after which the
+     *        instructions must be inserted.
+     * @param insns the instruction list to be inserted, which is cleared during
+     *        the process. This list must be different from 'this'.
+     */
+    public void insert(final AbstractInsnNode location, final InsnList insns) {
+        if (insns.size == 0) {
+            return;
+        }
+        size += insns.size;
+        AbstractInsnNode ifirst = insns.first;
+        AbstractInsnNode ilast = insns.last;
+        AbstractInsnNode next = location.next;
+        if (next == null) {
+            last = ilast;
+        } else {
+            next.prev = ilast;
+        }
+        location.next = ifirst;
+        ilast.next = next;
+        ifirst.prev = location;
+        cache = null;
+        insns.removeAll(false);
+    }
+
+    /**
+     * Inserts the given instruction before the specified instruction.
+     *
+     * @param location an instruction <i>of this list</i> before which insn must be
+     *        inserted.
+     * @param insn the instruction to be inserted, <i>which must not belong to
+     *        any {@link InsnList}</i>.
+     */
+    public void insertBefore(final AbstractInsnNode location, final AbstractInsnNode insn) {
+        ++size;
+        AbstractInsnNode prev = location.prev;
+        if (prev == null) {
+            first = insn;
+        } else {
+            prev.next = insn;
+        }
+        location.prev = insn;
+        insn.next = location;
+        insn.prev = prev;
+        cache = null;
+        insn.index = 0; // insn now belongs to an InsnList
+    }
+
+    /**
+     * Inserts the given instructions before the specified instruction.
+     *
+     * @param location  an instruction <i>of this list</i> before which the instructions
+     *        must be inserted.
+     * @param insns the instruction list to be inserted, which is cleared during
+     *        the process. This list must be different from 'this'.
+     */
+    public void insertBefore(final AbstractInsnNode location, final InsnList insns) {
+        if (insns.size == 0) {
+            return;
+        }
+        size += insns.size;
+        AbstractInsnNode ifirst = insns.first;
+        AbstractInsnNode ilast = insns.last;
+        AbstractInsnNode prev = location .prev;
+        if (prev == null) {
+            first = ifirst;
+        } else {
+            prev.next = ifirst;
+        }
+        location .prev = ilast;
+        ilast.next = location ;
+        ifirst.prev = prev;
+        cache = null;
+        insns.removeAll(false);
+    }
+
+
+
+    /**
+     * Removes the given instruction from this list.
+     *
+     * @param insn the instruction <i>of this list</i> that must be removed.
+     */
+    public void remove(final AbstractInsnNode insn) {
+        --size;
+        AbstractInsnNode next = insn.next;
+        AbstractInsnNode prev = insn.prev;
+        if (next == null) {
+            if (prev == null) {
+                first = null;
+                last = null;
+            } else {
+                prev.next = null;
+                last = prev;
+            }
+        } else {
+            if (prev == null) {
+                first = next;
+                next.prev = null;
+            } else {
+                prev.next = next;
+                next.prev = prev;
+            }
+        }
+        cache = null;
+        insn.index = -1; // insn no longer belongs to an InsnList
+        insn.prev = null;
+        insn.next = null;
+    }
+
+    /**
+     * Removes all of the instructions of this list.
+     *
+     * @param mark if the instructions must be marked as no longer belonging to
+     *        any {@link InsnList}.
+     */
+    void removeAll(final boolean mark) {
+        if (mark) {
+            AbstractInsnNode insn = first;
+            while (insn != null) {
+                AbstractInsnNode next = insn.next;
+                insn.index = -1; // insn no longer belongs to an InsnList
+                insn.prev = null;
+                insn.next = null;
+                insn = next;
+            }
+        }
+        size = 0;
+        first = null;
+        last = null;
+        cache = null;
+    }
+
+    /**
+     * Removes all of the instructions of this list.
+     */
+    public void clear() {
+        removeAll(false);
+    }
+
+    /**
+     * Reset all labels in the instruction list. This method should be called
+     * before reusing same instructions list between several
+     * <code>ClassWriter</code>s.
+     */
+    public void resetLabels() {
+        AbstractInsnNode insn = first;
+        while (insn != null) {
+            if (insn instanceof LabelNode) {
+                ((LabelNode) insn).resetLabel();
+            }
+            insn = insn.next;
+        }
+    }
+
+    // this class is not generified because it will create bridges
+    private final class InsnListIterator implements ListIterator/*<AbstractInsnNode>*/ {
+
+        AbstractInsnNode next;
+
+        AbstractInsnNode prev;
+
+        InsnListIterator(int index) {
+            if(index==size()) {
+                next = null;
+                prev = getLast();
+            } else {
+                next = get(index);
+                prev = next.prev;
+            }
+        }
+
+        public boolean hasNext() {
+            return next != null;
+        }
+
+        public Object next() {
+            if (next == null) {
+                throw new NoSuchElementException();
+            }
+            AbstractInsnNode result = next;
+            prev = result;
+            next = result.next;
+            return result;
+        }
+
+        public void remove() {
+            InsnList.this.remove(prev);
+            prev = prev.prev;
+        }
+
+        public boolean hasPrevious() {
+            return prev != null;
+        }
+
+        public Object previous() {
+            AbstractInsnNode result = prev;
+            next = result;
+            prev = result.prev;
+            return result;
+        }
+
+        public int nextIndex() {
+            if (next == null) {
+                return size();
+            }
+            if (cache == null) {
+                cache = toArray();
+            }
+            return next.index;
+        }
+
+        public int previousIndex() {
+            if (prev == null) {
+                return -1;
+            }
+            if (cache == null) {
+                cache = toArray();
+            }
+            return prev.index;
+        }
+
+        public void add(Object o) {
+            InsnList.this.insertBefore(next, (AbstractInsnNode) o);
+            prev = (AbstractInsnNode) o;
+        }
+
+        public void set(Object o) {
+            InsnList.this.set(next.prev, (AbstractInsnNode) o);
+            prev = (AbstractInsnNode) o;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/InsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,113 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a zero operand instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class InsnNode extends AbstractInsnNode {
+
+    /**
+     * Constructs a new {@link InsnNode}.
+     *
+     * @param opcode the opcode of the instruction to be constructed. This
+     *        opcode must be NOP, ACONST_NULL, ICONST_M1, ICONST_0, ICONST_1,
+     *        ICONST_2, ICONST_3, ICONST_4, ICONST_5, LCONST_0, LCONST_1,
+     *        FCONST_0, FCONST_1, FCONST_2, DCONST_0, DCONST_1, IALOAD, LALOAD,
+     *        FALOAD, DALOAD, AALOAD, BALOAD, CALOAD, SALOAD, IASTORE, LASTORE,
+     *        FASTORE, DASTORE, AASTORE, BASTORE, CASTORE, SASTORE, POP, POP2,
+     *        DUP, DUP_X1, DUP_X2, DUP2, DUP2_X1, DUP2_X2, SWAP, IADD, LADD,
+     *        FADD, DADD, ISUB, LSUB, FSUB, DSUB, IMUL, LMUL, FMUL, DMUL, IDIV,
+     *        LDIV, FDIV, DDIV, IREM, LREM, FREM, DREM, INEG, LNEG, FNEG, DNEG,
+     *        ISHL, LSHL, ISHR, LSHR, IUSHR, LUSHR, IAND, LAND, IOR, LOR, IXOR,
+     *        LXOR, I2L, I2F, I2D, L2I, L2F, L2D, F2I, F2L, F2D, D2I, D2L, D2F,
+     *        I2B, I2C, I2S, LCMP, FCMPL, FCMPG, DCMPL, DCMPG, IRETURN, LRETURN,
+     *        FRETURN, DRETURN, ARETURN, RETURN, ARRAYLENGTH, ATHROW,
+     *        MONITORENTER, or MONITOREXIT.
+     */
+    public InsnNode(final int opcode) {
+        super(opcode);
+    }
+
+    @Override
+    public int getType() {
+        return INSN;
+    }
+
+    /**
+     * Makes the given visitor visit this instruction.
+     *
+     * @param mv a method visitor.
+     */
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitInsn(opcode);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new InsnNode(opcode);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/IntInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,113 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents an instruction with a single int operand.
+ *
+ * @author Eric Bruneton
+ */
+public class IntInsnNode extends AbstractInsnNode {
+
+    /**
+     * The operand of this instruction.
+     */
+    public int operand;
+
+    /**
+     * Constructs a new {@link IntInsnNode}.
+     *
+     * @param opcode the opcode of the instruction to be constructed. This
+     *        opcode must be BIPUSH, SIPUSH or NEWARRAY.
+     * @param operand the operand of the instruction to be constructed.
+     */
+    public IntInsnNode(final int opcode, final int operand) {
+        super(opcode);
+        this.operand = operand;
+    }
+
+    /**
+     * Sets the opcode of this instruction.
+     *
+     * @param opcode the new instruction opcode. This opcode must be BIPUSH,
+     *        SIPUSH or NEWARRAY.
+     */
+    public void setOpcode(final int opcode) {
+        this.opcode = opcode;
+    }
+
+    @Override
+    public int getType() {
+        return INT_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitIntInsn(opcode, operand);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new IntInsnNode(opcode, operand);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/InvokeDynamicInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,129 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents an invokedynamic instruction.
+ *
+ * @author Remi Forax
+ */
+public class InvokeDynamicInsnNode extends AbstractInsnNode {
+
+    /**
+     * Invokedynamic name.
+     */
+    public String name;
+
+    /**
+     * Invokedynamic descriptor.
+     */
+    public String desc;
+
+    /**
+     * Bootstrap method
+     */
+    public Handle bsm;
+
+    /**
+     * Bootstrap constant arguments
+     */
+    public Object[] bsmArgs;
+
+    /**
+     * Constructs a new {@link InvokeDynamicInsnNode}.
+     *
+     * @param name invokedynamic name.
+     * @param desc invokedynamic descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     * @param bsm the bootstrap method.
+     * @param bsmArgs the boostrap constant arguments.
+     */
+    public InvokeDynamicInsnNode(
+        final String name,
+        final String desc,
+        final Handle bsm,
+        final Object... bsmArgs)
+    {
+        super(Opcodes.INVOKEDYNAMIC);
+        this.name = name;
+        this.desc = desc;
+        this.bsm = bsm;
+        this.bsmArgs = bsmArgs;
+    }
+
+    @Override
+    public int getType() {
+        return INVOKE_DYNAMIC_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new InvokeDynamicInsnNode(name, desc, bsm, bsmArgs);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/JumpInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,121 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a jump instruction. A jump instruction is an
+ * instruction that may jump to another instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class JumpInsnNode extends AbstractInsnNode {
+
+    /**
+     * The operand of this instruction. This operand is a label that designates
+     * the instruction to which this instruction may jump.
+     */
+    public LabelNode label;
+
+    /**
+     * Constructs a new {@link JumpInsnNode}.
+     *
+     * @param opcode the opcode of the type instruction to be constructed. This
+     *        opcode must be IFEQ, IFNE, IFLT, IFGE, IFGT, IFLE, IF_ICMPEQ,
+     *        IF_ICMPNE, IF_ICMPLT, IF_ICMPGE, IF_ICMPGT, IF_ICMPLE, IF_ACMPEQ,
+     *        IF_ACMPNE, GOTO, JSR, IFNULL or IFNONNULL.
+     * @param label the operand of the instruction to be constructed. This
+     *        operand is a label that designates the instruction to which the
+     *        jump instruction may jump.
+     */
+    public JumpInsnNode(final int opcode, final LabelNode label) {
+        super(opcode);
+        this.label = label;
+    }
+
+    /**
+     * Sets the opcode of this instruction.
+     *
+     * @param opcode the new instruction opcode. This opcode must be IFEQ, IFNE,
+     *        IFLT, IFGE, IFGT, IFLE, IF_ICMPEQ, IF_ICMPNE, IF_ICMPLT,
+     *        IF_ICMPGE, IF_ICMPGT, IF_ICMPLE, IF_ACMPEQ, IF_ACMPNE, GOTO, JSR,
+     *        IFNULL or IFNONNULL.
+     */
+    public void setOpcode(final int opcode) {
+        this.opcode = opcode;
+    }
+
+    @Override
+    public int getType() {
+        return JUMP_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitJumpInsn(opcode, label.getLabel());
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new JumpInsnNode(opcode, clone(label, labels));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/LabelNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,107 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * An {@link AbstractInsnNode} that encapsulates a {@link Label}.
+ */
+public class LabelNode extends AbstractInsnNode {
+
+    private Label label;
+
+    public LabelNode() {
+        super(-1);
+    }
+
+    public LabelNode(final Label label) {
+        super(-1);
+        this.label = label;
+    }
+
+    @Override
+    public int getType() {
+        return LABEL;
+    }
+
+    public Label getLabel() {
+        if (label == null) {
+            label = new Label();
+        }
+        return label;
+    }
+
+    @Override
+    public void accept(final MethodVisitor cv) {
+        cv.visitLabel(getLabel());
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return labels.get(this);
+    }
+
+    public void resetLabel() {
+        label = null;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/LdcInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,106 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents an LDC instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class LdcInsnNode extends AbstractInsnNode {
+
+    /**
+     * The constant to be loaded on the stack. This parameter must be a non null
+     * {@link Integer}, a {@link Float}, a {@link Long}, a {@link Double}, a
+     * {@link String} or a {@link jdk.internal.org.objectweb.asm.Type}.
+     */
+    public Object cst;
+
+    /**
+     * Constructs a new {@link LdcInsnNode}.
+     *
+     * @param cst the constant to be loaded on the stack. This parameter must be
+     *        a non null {@link Integer}, a {@link Float}, a {@link Long}, a
+     *        {@link Double} or a {@link String}.
+     */
+    public LdcInsnNode(final Object cst) {
+        super(Opcodes.LDC);
+        this.cst = cst;
+    }
+
+    @Override
+    public int getType() {
+        return LDC_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitLdcInsn(cst);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new LdcInsnNode(cst);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/LineNumberNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,111 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a line number declaration. These nodes are pseudo
+ * instruction nodes in order to be inserted in an instruction list.
+ *
+ * @author Eric Bruneton
+ */
+public class LineNumberNode extends AbstractInsnNode {
+
+    /**
+     * A line number. This number refers to the source file from which the class
+     * was compiled.
+     */
+    public int line;
+
+    /**
+     * The first instruction corresponding to this line number.
+     */
+    public LabelNode start;
+
+    /**
+     * Constructs a new {@link LineNumberNode}.
+     *
+     * @param line a line number. This number refers to the source file from
+     *        which the class was compiled.
+     * @param start the first instruction corresponding to this line number.
+     */
+    public LineNumberNode(final int line, final LabelNode start) {
+        super(-1);
+        this.line = line;
+        this.start = start;
+    }
+
+    @Override
+    public int getType() {
+        return LINE;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitLineNumber(line, start.getLabel());
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new LineNumberNode(line, clone(start, labels));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/LocalVariableNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,144 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a local variable declaration.
+ *
+ * @author Eric Bruneton
+ */
+public class LocalVariableNode {
+
+    /**
+     * The name of a local variable.
+     */
+    public String name;
+
+    /**
+     * The type descriptor of this local variable.
+     */
+    public String desc;
+
+    /**
+     * The signature of this local variable. May be <tt>null</tt>.
+     */
+    public String signature;
+
+    /**
+     * The first instruction corresponding to the scope of this local variable
+     * (inclusive).
+     */
+    public LabelNode start;
+
+    /**
+     * The last instruction corresponding to the scope of this local variable
+     * (exclusive).
+     */
+    public LabelNode end;
+
+    /**
+     * The local variable's index.
+     */
+    public int index;
+
+    /**
+     * Constructs a new {@link LocalVariableNode}.
+     *
+     * @param name the name of a local variable.
+     * @param desc the type descriptor of this local variable.
+     * @param signature the signature of this local variable. May be
+     *        <tt>null</tt>.
+     * @param start the first instruction corresponding to the scope of this
+     *        local variable (inclusive).
+     * @param end the last instruction corresponding to the scope of this local
+     *        variable (exclusive).
+     * @param index the local variable's index.
+     */
+    public LocalVariableNode(
+        final String name,
+        final String desc,
+        final String signature,
+        final LabelNode start,
+        final LabelNode end,
+        final int index)
+    {
+        this.name = name;
+        this.desc = desc;
+        this.signature = signature;
+        this.start = start;
+        this.end = end;
+        this.index = index;
+    }
+
+    /**
+     * Makes the given visitor visit this local variable declaration.
+     *
+     * @param mv a method visitor.
+     */
+    public void accept(final MethodVisitor mv) {
+        mv.visitLocalVariable(name,
+                desc,
+                signature,
+                start.getLabel(),
+                end.getLabel(),
+                index);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/LookupSwitchInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,145 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents a LOOKUPSWITCH instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class LookupSwitchInsnNode extends AbstractInsnNode {
+
+    /**
+     * Beginning of the default handler block.
+     */
+    public LabelNode dflt;
+
+    /**
+     * The values of the keys. This list is a list of {@link Integer} objects.
+     */
+    public List<Integer> keys;
+
+    /**
+     * Beginnings of the handler blocks. This list is a list of
+     * {@link LabelNode} objects.
+     */
+    public List<LabelNode> labels;
+
+    /**
+     * Constructs a new {@link LookupSwitchInsnNode}.
+     *
+     * @param dflt beginning of the default handler block.
+     * @param keys the values of the keys.
+     * @param labels beginnings of the handler blocks. <tt>labels[i]</tt> is
+     *        the beginning of the handler block for the <tt>keys[i]</tt> key.
+     */
+    public LookupSwitchInsnNode(
+        final LabelNode dflt,
+        final int[] keys,
+        final LabelNode[] labels)
+    {
+        super(Opcodes.LOOKUPSWITCH);
+        this.dflt = dflt;
+        this.keys = new ArrayList<Integer>(keys == null ? 0 : keys.length);
+        this.labels = new ArrayList<LabelNode>(labels == null ? 0 : labels.length);
+        if (keys != null) {
+            for (int i = 0; i < keys.length; ++i) {
+                this.keys.add(new Integer(keys[i]));
+            }
+        }
+        if (labels != null) {
+            this.labels.addAll(Arrays.asList(labels));
+        }
+    }
+
+    @Override
+    public int getType() {
+        return LOOKUPSWITCH_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        int[] keys = new int[this.keys.size()];
+        for (int i = 0; i < keys.length; ++i) {
+            keys[i] = this.keys.get(i).intValue();
+        }
+        Label[] labels = new Label[this.labels.size()];
+        for (int i = 0; i < labels.length; ++i) {
+            labels[i] = this.labels.get(i).getLabel();
+        }
+        mv.visitLookupSwitchInsn(dflt.getLabel(), keys, labels);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        LookupSwitchInsnNode clone = new LookupSwitchInsnNode(clone(dflt,
+                labels), null, clone(this.labels, labels));
+        clone.keys.addAll(keys);
+        return clone;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/MethodInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,136 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a method instruction. A method instruction is an
+ * instruction that invokes a method.
+ *
+ * @author Eric Bruneton
+ */
+public class MethodInsnNode extends AbstractInsnNode {
+
+    /**
+     * The internal name of the method's owner class (see
+     * {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     */
+    public String owner;
+
+    /**
+     * The method's name.
+     */
+    public String name;
+
+    /**
+     * The method's descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public String desc;
+
+    /**
+     * Constructs a new {@link MethodInsnNode}.
+     *
+     * @param opcode the opcode of the type instruction to be constructed. This
+     *        opcode must be INVOKEVIRTUAL, INVOKESPECIAL, INVOKESTATIC or
+     *        INVOKEINTERFACE.
+     * @param owner the internal name of the method's owner class (see
+     *        {@link jdk.internal.org.objectweb.asm.Type#getInternalName() getInternalName}).
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public MethodInsnNode(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        super(opcode);
+        this.owner = owner;
+        this.name = name;
+        this.desc = desc;
+    }
+
+    /**
+     * Sets the opcode of this instruction.
+     *
+     * @param opcode the new instruction opcode. This opcode must be
+     *        INVOKEVIRTUAL, INVOKESPECIAL, INVOKESTATIC or INVOKEINTERFACE.
+     */
+    public void setOpcode(final int opcode) {
+        this.opcode = opcode;
+    }
+
+    @Override
+    public int getType() {
+        return METHOD_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitMethodInsn(opcode, owner, name, desc);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new MethodInsnNode(opcode, owner, name, desc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/MethodNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,675 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A node that represents a method.
+ *
+ * @author Eric Bruneton
+ */
+public class MethodNode extends MethodVisitor {
+
+    /**
+     * The method's access flags (see {@link Opcodes}). This field also
+     * indicates if the method is synthetic and/or deprecated.
+     */
+    public int access;
+
+    /**
+     * The method's name.
+     */
+    public String name;
+
+    /**
+     * The method's descriptor (see {@link Type}).
+     */
+    public String desc;
+
+    /**
+     * The method's signature. May be <tt>null</tt>.
+     */
+    public String signature;
+
+    /**
+     * The internal names of the method's exception classes (see
+     * {@link Type#getInternalName() getInternalName}). This list is a list of
+     * {@link String} objects.
+     */
+    public List<String> exceptions;
+
+    /**
+     * The runtime visible annotations of this method. This list is a list of
+     * {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label visible
+     */
+    public List<AnnotationNode> visibleAnnotations;
+
+    /**
+     * The runtime invisible annotations of this method. This list is a list of
+     * {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label invisible
+     */
+    public List<AnnotationNode> invisibleAnnotations;
+
+    /**
+     * The non standard attributes of this method. This list is a list of
+     * {@link Attribute} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.Attribute
+     */
+    public List<Attribute> attrs;
+
+    /**
+     * The default value of this annotation interface method. This field must be
+     * a {@link Byte}, {@link Boolean}, {@link Character}, {@link Short},
+     * {@link Integer}, {@link Long}, {@link Float}, {@link Double},
+     * {@link String} or {@link Type}, or an two elements String array (for
+     * enumeration values), a {@link AnnotationNode}, or a {@link List} of
+     * values of one of the preceding types. May be <tt>null</tt>.
+     */
+    public Object annotationDefault;
+
+    /**
+     * The runtime visible parameter annotations of this method. These lists are
+     * lists of {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label invisible parameters
+     */
+    public List<AnnotationNode>[] visibleParameterAnnotations;
+
+    /**
+     * The runtime invisible parameter annotations of this method. These lists
+     * are lists of {@link AnnotationNode} objects. May be <tt>null</tt>.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AnnotationNode
+     * @label visible parameters
+     */
+    public List<AnnotationNode>[] invisibleParameterAnnotations;
+
+    /**
+     * The instructions of this method. This list is a list of
+     * {@link AbstractInsnNode} objects.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.AbstractInsnNode
+     * @label instructions
+     */
+    public InsnList instructions;
+
+    /**
+     * The try catch blocks of this method. This list is a list of
+     * {@link TryCatchBlockNode} objects.
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.TryCatchBlockNode
+     */
+    public List<TryCatchBlockNode> tryCatchBlocks;
+
+    /**
+     * The maximum stack size of this method.
+     */
+    public int maxStack;
+
+    /**
+     * The maximum number of local variables of this method.
+     */
+    public int maxLocals;
+
+    /**
+     * The local variables of this method. This list is a list of
+     * {@link LocalVariableNode} objects. May be <tt>null</tt>
+     *
+     * @associates jdk.internal.org.objectweb.asm.tree.LocalVariableNode
+     */
+    public List<LocalVariableNode> localVariables;
+
+    /**
+     * If the accept method has been called on this object.
+     */
+    private boolean visited;
+
+    /**
+     * Constructs an uninitialized {@link MethodNode}. <i>Subclasses must not
+     * use this constructor</i>. Instead, they must use the
+     * {@link #MethodNode(int)} version.
+     */
+    public MethodNode() {
+        this(Opcodes.ASM4);
+    }
+
+    /**
+     * Constructs an uninitialized {@link MethodNode}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    public MethodNode(final int api) {
+        super(api);
+        this.instructions = new InsnList();
+    }
+
+    /**
+     * Constructs a new {@link MethodNode}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #MethodNode(int, int, String, String, String, String[])} version.
+     *
+     * @param access the method's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the method is synthetic and/or
+     *        deprecated.
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type}).
+     * @param signature the method's signature. May be <tt>null</tt>.
+     * @param exceptions the internal names of the method's exception classes
+     *        (see {@link Type#getInternalName() getInternalName}). May be
+     *        <tt>null</tt>.
+     */
+    public MethodNode(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        this(Opcodes.ASM4, access, name, desc, signature, exceptions);
+    }
+
+    /**
+     * Constructs a new {@link MethodNode}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param access the method's access flags (see {@link Opcodes}). This
+     *        parameter also indicates if the method is synthetic and/or
+     *        deprecated.
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type}).
+     * @param signature the method's signature. May be <tt>null</tt>.
+     * @param exceptions the internal names of the method's exception classes
+     *        (see {@link Type#getInternalName() getInternalName}). May be
+     *        <tt>null</tt>.
+     */
+    public MethodNode(
+        final int api,
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        super(api);
+        this.access = access;
+        this.name = name;
+        this.desc = desc;
+        this.signature = signature;
+        this.exceptions = new ArrayList<String>(exceptions == null
+                ? 0
+                : exceptions.length);
+        boolean isAbstract = (access & Opcodes.ACC_ABSTRACT) != 0;
+        if (!isAbstract) {
+            this.localVariables = new ArrayList<LocalVariableNode>(5);
+        }
+        this.tryCatchBlocks = new ArrayList<TryCatchBlockNode>();
+        if (exceptions != null) {
+            this.exceptions.addAll(Arrays.asList(exceptions));
+        }
+        this.instructions = new InsnList();
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the MethodVisitor abstract class
+    // ------------------------------------------------------------------------
+
+    @Override
+    public AnnotationVisitor visitAnnotationDefault() {
+        return new AnnotationNode(new ArrayList<Object>(0) {
+            @Override
+            public boolean add(final Object o) {
+                annotationDefault = o;
+                return super.add(o);
+            }
+        });
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        AnnotationNode an = new AnnotationNode(desc);
+        if (visible) {
+            if (visibleAnnotations == null) {
+                visibleAnnotations = new ArrayList<AnnotationNode>(1);
+            }
+            visibleAnnotations.add(an);
+        } else {
+            if (invisibleAnnotations == null) {
+                invisibleAnnotations = new ArrayList<AnnotationNode>(1);
+            }
+            invisibleAnnotations.add(an);
+        }
+        return an;
+    }
+
+    @Override
+    public AnnotationVisitor visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible)
+    {
+        AnnotationNode an = new AnnotationNode(desc);
+        if (visible) {
+            if (visibleParameterAnnotations == null) {
+                int params = Type.getArgumentTypes(this.desc).length;
+                visibleParameterAnnotations = (List<AnnotationNode>[])new List<?>[params];
+            }
+            if (visibleParameterAnnotations[parameter] == null) {
+                visibleParameterAnnotations[parameter] = new ArrayList<AnnotationNode>(1);
+            }
+            visibleParameterAnnotations[parameter].add(an);
+        } else {
+            if (invisibleParameterAnnotations == null) {
+                int params = Type.getArgumentTypes(this.desc).length;
+                invisibleParameterAnnotations = (List<AnnotationNode>[])new List<?>[params];
+            }
+            if (invisibleParameterAnnotations[parameter] == null) {
+                invisibleParameterAnnotations[parameter] = new ArrayList<AnnotationNode>(1);
+            }
+            invisibleParameterAnnotations[parameter].add(an);
+        }
+        return an;
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        if (attrs == null) {
+            attrs = new ArrayList<Attribute>(1);
+        }
+        attrs.add(attr);
+    }
+
+    @Override
+    public void visitCode() {
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        instructions.add(new FrameNode(type, nLocal, local == null
+                ? null
+                : getLabelNodes(local), nStack, stack == null
+                ? null
+                : getLabelNodes(stack)));
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        instructions.add(new InsnNode(opcode));
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        instructions.add(new IntInsnNode(opcode, operand));
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        instructions.add(new VarInsnNode(opcode, var));
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        instructions.add(new TypeInsnNode(opcode, type));
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        instructions.add(new FieldInsnNode(opcode, owner, name, desc));
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        instructions.add(new MethodInsnNode(opcode, owner, name, desc));
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        instructions.add(new InvokeDynamicInsnNode(name, desc, bsm, bsmArgs));
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        instructions.add(new JumpInsnNode(opcode, getLabelNode(label)));
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        instructions.add(getLabelNode(label));
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        instructions.add(new LdcInsnNode(cst));
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        instructions.add(new IincInsnNode(var, increment));
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        instructions.add(new TableSwitchInsnNode(min,
+                max,
+                getLabelNode(dflt),
+                getLabelNodes(labels)));
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        instructions.add(new LookupSwitchInsnNode(getLabelNode(dflt),
+                keys,
+                getLabelNodes(labels)));
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        instructions.add(new MultiANewArrayInsnNode(desc, dims));
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type)
+    {
+        tryCatchBlocks.add(new TryCatchBlockNode(getLabelNode(start),
+                getLabelNode(end),
+                getLabelNode(handler),
+                type));
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        localVariables.add(new LocalVariableNode(name,
+                desc,
+                signature,
+                getLabelNode(start),
+                getLabelNode(end),
+                index));
+    }
+
+    @Override
+    public void visitLineNumber(final int line, final Label start) {
+        instructions.add(new LineNumberNode(line, getLabelNode(start)));
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        this.maxStack = maxStack;
+        this.maxLocals = maxLocals;
+    }
+
+    @Override
+    public void visitEnd() {
+    }
+
+    /**
+     * Returns the LabelNode corresponding to the given Label. Creates a new
+     * LabelNode if necessary. The default implementation of this method uses
+     * the {@link Label#info} field to store associations between labels and
+     * label nodes.
+     *
+     * @param l a Label.
+     * @return the LabelNode corresponding to l.
+     */
+    protected LabelNode getLabelNode(final Label l) {
+        if (!(l.info instanceof LabelNode)) {
+            l.info = new LabelNode(l);
+        }
+        return (LabelNode) l.info;
+    }
+
+    private LabelNode[] getLabelNodes(final Label[] l) {
+        LabelNode[] nodes = new LabelNode[l.length];
+        for (int i = 0; i < l.length; ++i) {
+            nodes[i] = getLabelNode(l[i]);
+        }
+        return nodes;
+    }
+
+    private Object[] getLabelNodes(final Object[] objs) {
+        Object[] nodes = new Object[objs.length];
+        for (int i = 0; i < objs.length; ++i) {
+            Object o = objs[i];
+            if (o instanceof Label) {
+                o = getLabelNode((Label) o);
+            }
+            nodes[i] = o;
+        }
+        return nodes;
+    }
+
+    // ------------------------------------------------------------------------
+    // Accept method
+    // ------------------------------------------------------------------------
+
+    /**
+     * Checks that this method node is compatible with the given ASM API
+     * version. This methods checks that this node, and all its nodes
+     * recursively, do not contain elements that were introduced in more recent
+     * versions of the ASM API than the given version.
+     *
+     * @param api an ASM API version. Must be one of {@link Opcodes#ASM4}.
+     */
+    public void check(final int api) {
+        // nothing to do
+    }
+
+    /**
+     * Makes the given class visitor visit this method.
+     *
+     * @param cv a class visitor.
+     */
+    public void accept(final ClassVisitor cv) {
+        String[] exceptions = new String[this.exceptions.size()];
+        this.exceptions.toArray(exceptions);
+        MethodVisitor mv = cv.visitMethod(access,
+                name,
+                desc,
+                signature,
+                exceptions);
+        if (mv != null) {
+            accept(mv);
+        }
+    }
+
+    /**
+     * Makes the given method visitor visit this method.
+     *
+     * @param mv a method visitor.
+     */
+    public void accept(final MethodVisitor mv) {
+        // visits the method attributes
+        int i, j, n;
+        if (annotationDefault != null) {
+            AnnotationVisitor av = mv.visitAnnotationDefault();
+            AnnotationNode.accept(av, null, annotationDefault);
+            if (av != null) {
+                av.visitEnd();
+            }
+        }
+        n = visibleAnnotations == null ? 0 : visibleAnnotations.size();
+        for (i = 0; i < n; ++i) {
+            AnnotationNode an = visibleAnnotations.get(i);
+            an.accept(mv.visitAnnotation(an.desc, true));
+        }
+        n = invisibleAnnotations == null ? 0 : invisibleAnnotations.size();
+        for (i = 0; i < n; ++i) {
+            AnnotationNode an = invisibleAnnotations.get(i);
+            an.accept(mv.visitAnnotation(an.desc, false));
+        }
+        n = visibleParameterAnnotations == null
+                ? 0
+                : visibleParameterAnnotations.length;
+        for (i = 0; i < n; ++i) {
+            List<?> l = visibleParameterAnnotations[i];
+            if (l == null) {
+                continue;
+            }
+            for (j = 0; j < l.size(); ++j) {
+                AnnotationNode an = (AnnotationNode) l.get(j);
+                an.accept(mv.visitParameterAnnotation(i, an.desc, true));
+            }
+        }
+        n = invisibleParameterAnnotations == null
+                ? 0
+                : invisibleParameterAnnotations.length;
+        for (i = 0; i < n; ++i) {
+            List<?> l = invisibleParameterAnnotations[i];
+            if (l == null) {
+                continue;
+            }
+            for (j = 0; j < l.size(); ++j) {
+                AnnotationNode an = (AnnotationNode) l.get(j);
+                an.accept(mv.visitParameterAnnotation(i, an.desc, false));
+            }
+        }
+        if (visited) {
+            instructions.resetLabels();
+        }
+        n = attrs == null ? 0 : attrs.size();
+        for (i = 0; i < n; ++i) {
+            mv.visitAttribute(attrs.get(i));
+        }
+        // visits the method's code
+        if (instructions.size() > 0) {
+            mv.visitCode();
+            // visits try catch blocks
+            n = tryCatchBlocks == null ? 0 : tryCatchBlocks.size();
+            for (i = 0; i < n; ++i) {
+                tryCatchBlocks.get(i).accept(mv);
+            }
+            // visits instructions
+            instructions.accept(mv);
+            // visits local variables
+            n = localVariables == null ? 0 : localVariables.size();
+            for (i = 0; i < n; ++i) {
+                localVariables.get(i).accept(mv);
+            }
+            // visits maxs
+            mv.visitMaxs(maxStack, maxLocals);
+            visited = true;
+        }
+        mv.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/MultiANewArrayInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,110 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents a MULTIANEWARRAY instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class MultiANewArrayInsnNode extends AbstractInsnNode {
+
+    /**
+     * An array type descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public String desc;
+
+    /**
+     * Number of dimensions of the array to allocate.
+     */
+    public int dims;
+
+    /**
+     * Constructs a new {@link MultiANewArrayInsnNode}.
+     *
+     * @param desc an array type descriptor (see {@link jdk.internal.org.objectweb.asm.Type}).
+     * @param dims number of dimensions of the array to allocate.
+     */
+    public MultiANewArrayInsnNode(final String desc, final int dims) {
+        super(Opcodes.MULTIANEWARRAY);
+        this.desc = desc;
+        this.dims = dims;
+    }
+
+    @Override
+    public int getType() {
+        return MULTIANEWARRAY_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitMultiANewArrayInsn(desc, dims);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new MultiANewArrayInsnNode(desc, dims);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/TableSwitchInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,144 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A node that represents a TABLESWITCH instruction.
+ *
+ * @author Eric Bruneton
+ */
+public class TableSwitchInsnNode extends AbstractInsnNode {
+
+    /**
+     * The minimum key value.
+     */
+    public int min;
+
+    /**
+     * The maximum key value.
+     */
+    public int max;
+
+    /**
+     * Beginning of the default handler block.
+     */
+    public LabelNode dflt;
+
+    /**
+     * Beginnings of the handler blocks. This list is a list of
+     * {@link LabelNode} objects.
+     */
+    public List<LabelNode> labels;
+
+    /**
+     * Constructs a new {@link TableSwitchInsnNode}.
+     *
+     * @param min the minimum key value.
+     * @param max the maximum key value.
+     * @param dflt beginning of the default handler block.
+     * @param labels beginnings of the handler blocks. <tt>labels[i]</tt> is
+     *        the beginning of the handler block for the <tt>min + i</tt> key.
+     */
+    public TableSwitchInsnNode(
+        final int min,
+        final int max,
+        final LabelNode dflt,
+        final LabelNode... labels)
+    {
+        super(Opcodes.TABLESWITCH);
+        this.min = min;
+        this.max = max;
+        this.dflt = dflt;
+        this.labels = new ArrayList<LabelNode>();
+        if (labels != null) {
+            this.labels.addAll(Arrays.asList(labels));
+        }
+    }
+
+    @Override
+    public int getType() {
+        return TABLESWITCH_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        Label[] labels = new Label[this.labels.size()];
+        for (int i = 0; i < labels.length; ++i) {
+            labels[i] = this.labels.get(i).getLabel();
+        }
+        mv.visitTableSwitchInsn(min, max, dflt.getLabel(), labels);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new TableSwitchInsnNode(min,
+                max,
+                clone(dflt, labels),
+                clone(this.labels, labels));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/TryCatchBlockNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,123 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a try catch block.
+ *
+ * @author Eric Bruneton
+ */
+public class TryCatchBlockNode {
+
+    /**
+     * Beginning of the exception handler's scope (inclusive).
+     */
+    public LabelNode start;
+
+    /**
+     * End of the exception handler's scope (exclusive).
+     */
+    public LabelNode end;
+
+    /**
+     * Beginning of the exception handler's code.
+     */
+    public LabelNode handler;
+
+    /**
+     * Internal name of the type of exceptions handled by the handler. May be
+     * <tt>null</tt> to catch any exceptions (for "finally" blocks).
+     */
+    public String type;
+
+    /**
+     * Constructs a new {@link TryCatchBlockNode}.
+     *
+     * @param start beginning of the exception handler's scope (inclusive).
+     * @param end end of the exception handler's scope (exclusive).
+     * @param handler beginning of the exception handler's code.
+     * @param type internal name of the type of exceptions handled by the
+     *        handler, or <tt>null</tt> to catch any exceptions (for "finally"
+     *        blocks).
+     */
+    public TryCatchBlockNode(
+        final LabelNode start,
+        final LabelNode end,
+        final LabelNode handler,
+        final String type)
+    {
+        this.start = start;
+        this.end = end;
+        this.handler = handler;
+        this.type = type;
+    }
+
+    /**
+     * Makes the given visitor visit this try catch block.
+     *
+     * @param mv a method visitor.
+     */
+    public void accept(final MethodVisitor mv) {
+        mv.visitTryCatchBlock(start.getLabel(), end.getLabel(), handler == null
+                ? null
+                : handler.getLabel(), type);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/TypeInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,116 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a type instruction. A type instruction is an
+ * instruction that takes a type descriptor as parameter.
+ *
+ * @author Eric Bruneton
+ */
+public class TypeInsnNode extends AbstractInsnNode {
+
+    /**
+     * The operand of this instruction. This operand is an internal name (see
+     * {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public String desc;
+
+    /**
+     * Constructs a new {@link TypeInsnNode}.
+     *
+     * @param opcode the opcode of the type instruction to be constructed. This
+     *        opcode must be NEW, ANEWARRAY, CHECKCAST or INSTANCEOF.
+     * @param desc the operand of the instruction to be constructed. This
+     *        operand is an internal name (see {@link jdk.internal.org.objectweb.asm.Type}).
+     */
+    public TypeInsnNode(final int opcode, final String desc) {
+        super(opcode);
+        this.desc = desc;
+    }
+
+    /**
+     * Sets the opcode of this instruction.
+     *
+     * @param opcode the new instruction opcode. This opcode must be NEW,
+     *        ANEWARRAY, CHECKCAST or INSTANCEOF.
+     */
+    public void setOpcode(final int opcode) {
+        this.opcode = opcode;
+    }
+
+    @Override
+    public int getType() {
+        return TYPE_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitTypeInsn(opcode, desc);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new TypeInsnNode(opcode, desc);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/VarInsnNode.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,119 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+
+/**
+ * A node that represents a local variable instruction. A local variable
+ * instruction is an instruction that loads or stores the value of a local
+ * variable.
+ *
+ * @author Eric Bruneton
+ */
+public class VarInsnNode extends AbstractInsnNode {
+
+    /**
+     * The operand of this instruction. This operand is the index of a local
+     * variable.
+     */
+    public int var;
+
+    /**
+     * Constructs a new {@link VarInsnNode}.
+     *
+     * @param opcode the opcode of the local variable instruction to be
+     *        constructed. This opcode must be ILOAD, LLOAD, FLOAD, DLOAD,
+     *        ALOAD, ISTORE, LSTORE, FSTORE, DSTORE, ASTORE or RET.
+     * @param var the operand of the instruction to be constructed. This operand
+     *        is the index of a local variable.
+     */
+    public VarInsnNode(final int opcode, final int var) {
+        super(opcode);
+        this.var = var;
+    }
+
+    /**
+     * Sets the opcode of this instruction.
+     *
+     * @param opcode the new instruction opcode. This opcode must be ILOAD,
+     *        LLOAD, FLOAD, DLOAD, ALOAD, ISTORE, LSTORE, FSTORE, DSTORE, ASTORE
+     *        or RET.
+     */
+    public void setOpcode(final int opcode) {
+        this.opcode = opcode;
+    }
+
+    @Override
+    public int getType() {
+        return VAR_INSN;
+    }
+
+    @Override
+    public void accept(final MethodVisitor mv) {
+        mv.visitVarInsn(opcode, var);
+    }
+
+    @Override
+    public AbstractInsnNode clone(final Map<LabelNode, LabelNode> labels) {
+        return new VarInsnNode(opcode, var);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/Analyzer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,579 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+import jdk.internal.org.objectweb.asm.tree.IincInsnNode;
+import jdk.internal.org.objectweb.asm.tree.InsnList;
+import jdk.internal.org.objectweb.asm.tree.JumpInsnNode;
+import jdk.internal.org.objectweb.asm.tree.LabelNode;
+import jdk.internal.org.objectweb.asm.tree.LookupSwitchInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MethodNode;
+import jdk.internal.org.objectweb.asm.tree.TableSwitchInsnNode;
+import jdk.internal.org.objectweb.asm.tree.TryCatchBlockNode;
+import jdk.internal.org.objectweb.asm.tree.VarInsnNode;
+
+/**
+ * A semantic bytecode analyzer. <i>This class does not fully check that JSR and
+ * RET instructions are valid.</i>
+ *
+ * @param <V> type of the Value used for the analysis.
+ *
+ *  @author Eric Bruneton
+ */
+public class Analyzer<V extends Value> implements Opcodes {
+
+    private final Interpreter<V> interpreter;
+
+    private int n;
+
+    private InsnList insns;
+
+    private List<TryCatchBlockNode>[] handlers;
+
+    private Frame<V>[] frames;
+
+    private Subroutine[] subroutines;
+
+    private boolean[] queued;
+
+    private int[] queue;
+
+    private int top;
+
+    /**
+     * Constructs a new {@link Analyzer}.
+     *
+     * @param interpreter the interpreter to be used to symbolically interpret
+     *        the bytecode instructions.
+     */
+    public Analyzer(final Interpreter<V> interpreter) {
+        this.interpreter = interpreter;
+    }
+
+    /**
+     * Analyzes the given method.
+     *
+     * @param owner the internal name of the class to which the method belongs.
+     * @param m the method to be analyzed.
+     * @return the symbolic state of the execution stack frame at each bytecode
+     *         instruction of the method. The size of the returned array is
+     *         equal to the number of instructions (and labels) of the method. A
+     *         given frame is <tt>null</tt> if and only if the corresponding
+     *         instruction cannot be reached (dead code).
+     * @throws AnalyzerException if a problem occurs during the analysis.
+     */
+    public Frame<V>[] analyze(final String owner, final MethodNode m)
+            throws AnalyzerException
+    {
+        if ((m.access & (ACC_ABSTRACT | ACC_NATIVE)) != 0) {
+            frames = (Frame<V>[])new Frame<?>[0];
+            return frames;
+        }
+        n = m.instructions.size();
+        insns = m.instructions;
+        handlers = (List<TryCatchBlockNode>[])new List<?>[n];
+        frames = (Frame<V>[])new Frame<?>[n];
+        subroutines = new Subroutine[n];
+        queued = new boolean[n];
+        queue = new int[n];
+        top = 0;
+
+        // computes exception handlers for each instruction
+        for (int i = 0; i < m.tryCatchBlocks.size(); ++i) {
+            TryCatchBlockNode tcb = m.tryCatchBlocks.get(i);
+            int begin = insns.indexOf(tcb.start);
+            int end = insns.indexOf(tcb.end);
+            for (int j = begin; j < end; ++j) {
+                List<TryCatchBlockNode> insnHandlers = handlers[j];
+                if (insnHandlers == null) {
+                    insnHandlers = new ArrayList<TryCatchBlockNode>();
+                    handlers[j] = insnHandlers;
+                }
+                insnHandlers.add(tcb);
+            }
+        }
+
+        // computes the subroutine for each instruction:
+        Subroutine main = new Subroutine(null, m.maxLocals, null);
+        List<AbstractInsnNode> subroutineCalls = new ArrayList<AbstractInsnNode>();
+        Map<LabelNode, Subroutine> subroutineHeads = new HashMap<LabelNode, Subroutine>();
+        findSubroutine(0, main, subroutineCalls);
+        while (!subroutineCalls.isEmpty()) {
+            JumpInsnNode jsr = (JumpInsnNode) subroutineCalls.remove(0);
+            Subroutine sub = subroutineHeads.get(jsr.label);
+            if (sub == null) {
+                sub = new Subroutine(jsr.label, m.maxLocals, jsr);
+                subroutineHeads.put(jsr.label, sub);
+                findSubroutine(insns.indexOf(jsr.label), sub, subroutineCalls);
+            } else {
+                sub.callers.add(jsr);
+            }
+        }
+        for (int i = 0; i < n; ++i) {
+            if (subroutines[i] != null && subroutines[i].start == null) {
+                subroutines[i] = null;
+            }
+        }
+
+        // initializes the data structures for the control flow analysis
+        Frame<V> current = newFrame(m.maxLocals, m.maxStack);
+        Frame<V> handler = newFrame(m.maxLocals, m.maxStack);
+        current.setReturn(interpreter.newValue(Type.getReturnType(m.desc)));
+        Type[] args = Type.getArgumentTypes(m.desc);
+        int local = 0;
+        if ((m.access & ACC_STATIC) == 0) {
+            Type ctype = Type.getObjectType(owner);
+            current.setLocal(local++, interpreter.newValue(ctype));
+        }
+        for (int i = 0; i < args.length; ++i) {
+            current.setLocal(local++, interpreter.newValue(args[i]));
+            if (args[i].getSize() == 2) {
+                current.setLocal(local++, interpreter.newValue(null));
+            }
+        }
+        while (local < m.maxLocals) {
+            current.setLocal(local++, interpreter.newValue(null));
+        }
+        merge(0, current, null);
+
+        init(owner, m);
+
+        // control flow analysis
+        while (top > 0) {
+            int insn = queue[--top];
+            Frame<V> f = frames[insn];
+            Subroutine subroutine = subroutines[insn];
+            queued[insn] = false;
+
+            AbstractInsnNode insnNode = null;
+            try {
+                insnNode = m.instructions.get(insn);
+                int insnOpcode = insnNode.getOpcode();
+                int insnType = insnNode.getType();
+
+                if (insnType == AbstractInsnNode.LABEL
+                        || insnType == AbstractInsnNode.LINE
+                        || insnType == AbstractInsnNode.FRAME)
+                {
+                    merge(insn + 1, f, subroutine);
+                    newControlFlowEdge(insn, insn + 1);
+                } else {
+                    current.init(f).execute(insnNode, interpreter);
+                    subroutine = subroutine == null ? null : subroutine.copy();
+
+                    if (insnNode instanceof JumpInsnNode) {
+                        JumpInsnNode j = (JumpInsnNode) insnNode;
+                        if (insnOpcode != GOTO && insnOpcode != JSR) {
+                            merge(insn + 1, current, subroutine);
+                            newControlFlowEdge(insn, insn + 1);
+                        }
+                        int jump = insns.indexOf(j.label);
+                        if (insnOpcode == JSR) {
+                            merge(jump, current, new Subroutine(j.label,
+                                    m.maxLocals,
+                                    j));
+                        } else {
+                            merge(jump, current, subroutine);
+                        }
+                        newControlFlowEdge(insn, jump);
+                    } else if (insnNode instanceof LookupSwitchInsnNode) {
+                        LookupSwitchInsnNode lsi = (LookupSwitchInsnNode) insnNode;
+                        int jump = insns.indexOf(lsi.dflt);
+                        merge(jump, current, subroutine);
+                        newControlFlowEdge(insn, jump);
+                        for (int j = 0; j < lsi.labels.size(); ++j) {
+                            LabelNode label = lsi.labels.get(j);
+                            jump = insns.indexOf(label);
+                            merge(jump, current, subroutine);
+                            newControlFlowEdge(insn, jump);
+                        }
+                    } else if (insnNode instanceof TableSwitchInsnNode) {
+                        TableSwitchInsnNode tsi = (TableSwitchInsnNode) insnNode;
+                        int jump = insns.indexOf(tsi.dflt);
+                        merge(jump, current, subroutine);
+                        newControlFlowEdge(insn, jump);
+                        for (int j = 0; j < tsi.labels.size(); ++j) {
+                            LabelNode label = tsi.labels.get(j);
+                            jump = insns.indexOf(label);
+                            merge(jump, current, subroutine);
+                            newControlFlowEdge(insn, jump);
+                        }
+                    } else if (insnOpcode == RET) {
+                        if (subroutine == null) {
+                            throw new AnalyzerException(insnNode, "RET instruction outside of a sub routine");
+                        }
+                        for (int i = 0; i < subroutine.callers.size(); ++i) {
+                            JumpInsnNode caller = subroutine.callers.get(i);
+                            int call = insns.indexOf(caller);
+                            if (frames[call] != null) {
+                                merge(call + 1,
+                                        frames[call],
+                                        current,
+                                        subroutines[call],
+                                        subroutine.access);
+                                newControlFlowEdge(insn, call + 1);
+                            }
+                        }
+                    } else if (insnOpcode != ATHROW
+                            && (insnOpcode < IRETURN || insnOpcode > RETURN))
+                    {
+                        if (subroutine != null) {
+                            if (insnNode instanceof VarInsnNode) {
+                                int var = ((VarInsnNode) insnNode).var;
+                                subroutine.access[var] = true;
+                                if (insnOpcode == LLOAD || insnOpcode == DLOAD
+                                        || insnOpcode == LSTORE
+                                        || insnOpcode == DSTORE)
+                                {
+                                    subroutine.access[var + 1] = true;
+                                }
+                            } else if (insnNode instanceof IincInsnNode) {
+                                int var = ((IincInsnNode) insnNode).var;
+                                subroutine.access[var] = true;
+                            }
+                        }
+                        merge(insn + 1, current, subroutine);
+                        newControlFlowEdge(insn, insn + 1);
+                    }
+                }
+
+                List<TryCatchBlockNode> insnHandlers = handlers[insn];
+                if (insnHandlers != null) {
+                    for (int i = 0; i < insnHandlers.size(); ++i) {
+                        TryCatchBlockNode tcb = insnHandlers.get(i);
+                        Type type;
+                        if (tcb.type == null) {
+                            type = Type.getObjectType("java/lang/Throwable");
+                        } else {
+                            type = Type.getObjectType(tcb.type);
+                        }
+                        int jump = insns.indexOf(tcb.handler);
+                        if (newControlFlowExceptionEdge(insn, tcb)) {
+                            handler.init(f);
+                            handler.clearStack();
+                            handler.push(interpreter.newValue(type));
+                            merge(jump, handler, subroutine);
+                        }
+                    }
+                }
+            } catch (AnalyzerException e) {
+                throw new AnalyzerException(e.node, "Error at instruction " + insn
+                        + ": " + e.getMessage(), e);
+            } catch (Exception e) {
+                throw new AnalyzerException(insnNode, "Error at instruction " + insn
+                        + ": " + e.getMessage(), e);
+            }
+        }
+
+        return frames;
+    }
+
+    private void findSubroutine(int insn, final Subroutine sub, final List<AbstractInsnNode> calls)
+            throws AnalyzerException
+    {
+        while (true) {
+            if (insn < 0 || insn >= n) {
+                throw new AnalyzerException(null, "Execution can fall off end of the code");
+            }
+            if (subroutines[insn] != null) {
+                return;
+            }
+            subroutines[insn] = sub.copy();
+            AbstractInsnNode node = insns.get(insn);
+
+            // calls findSubroutine recursively on normal successors
+            if (node instanceof JumpInsnNode) {
+                if (node.getOpcode() == JSR) {
+                    // do not follow a JSR, it leads to another subroutine!
+                    calls.add(node);
+                } else {
+                    JumpInsnNode jnode = (JumpInsnNode) node;
+                    findSubroutine(insns.indexOf(jnode.label), sub, calls);
+                }
+            } else if (node instanceof TableSwitchInsnNode) {
+                TableSwitchInsnNode tsnode = (TableSwitchInsnNode) node;
+                findSubroutine(insns.indexOf(tsnode.dflt), sub, calls);
+                for (int i = tsnode.labels.size() - 1; i >= 0; --i) {
+                    LabelNode l = tsnode.labels.get(i);
+                    findSubroutine(insns.indexOf(l), sub, calls);
+                }
+            } else if (node instanceof LookupSwitchInsnNode) {
+                LookupSwitchInsnNode lsnode = (LookupSwitchInsnNode) node;
+                findSubroutine(insns.indexOf(lsnode.dflt), sub, calls);
+                for (int i = lsnode.labels.size() - 1; i >= 0; --i) {
+                    LabelNode l = lsnode.labels.get(i);
+                    findSubroutine(insns.indexOf(l), sub, calls);
+                }
+            }
+
+            // calls findSubroutine recursively on exception handler successors
+            List<TryCatchBlockNode> insnHandlers = handlers[insn];
+            if (insnHandlers != null) {
+                for (int i = 0; i < insnHandlers.size(); ++i) {
+                    TryCatchBlockNode tcb = insnHandlers.get(i);
+                    findSubroutine(insns.indexOf(tcb.handler), sub, calls);
+                }
+            }
+
+            // if insn does not falls through to the next instruction, return.
+            switch (node.getOpcode()) {
+                case GOTO:
+                case RET:
+                case TABLESWITCH:
+                case LOOKUPSWITCH:
+                case IRETURN:
+                case LRETURN:
+                case FRETURN:
+                case DRETURN:
+                case ARETURN:
+                case RETURN:
+                case ATHROW:
+                    return;
+            }
+            insn++;
+        }
+    }
+
+    /**
+     * Returns the symbolic stack frame for each instruction of the last
+     * recently analyzed method.
+     *
+     * @return the symbolic state of the execution stack frame at each bytecode
+     *         instruction of the method. The size of the returned array is
+     *         equal to the number of instructions (and labels) of the method. A
+     *         given frame is <tt>null</tt> if the corresponding instruction
+     *         cannot be reached, or if an error occured during the analysis of
+     *         the method.
+     */
+    public Frame<V>[] getFrames() {
+        return frames;
+    }
+
+    /**
+     * Returns the exception handlers for the given instruction.
+     *
+     * @param insn the index of an instruction of the last recently analyzed
+     *        method.
+     * @return a list of {@link TryCatchBlockNode} objects.
+     */
+    public List<TryCatchBlockNode> getHandlers(final int insn) {
+        return handlers[insn];
+    }
+
+    /**
+     * Initializes this analyzer. This method is called just before the
+     * execution of control flow analysis loop in #analyze. The default
+     * implementation of this method does nothing.
+     *
+     * @param owner the internal name of the class to which the method belongs.
+     * @param m the method to be analyzed.
+     * @throws AnalyzerException if a problem occurs.
+     */
+    protected void init(String owner, MethodNode m) throws AnalyzerException {
+    }
+
+    /**
+     * Constructs a new frame with the given size.
+     *
+     * @param nLocals the maximum number of local variables of the frame.
+     * @param nStack the maximum stack size of the frame.
+     * @return the created frame.
+     */
+    protected Frame<V> newFrame(final int nLocals, final int nStack) {
+        return new Frame<V>(nLocals, nStack);
+    }
+
+    /**
+     * Constructs a new frame that is identical to the given frame.
+     *
+     * @param src a frame.
+     * @return the created frame.
+     */
+    protected Frame<V> newFrame(final Frame<? extends V> src) {
+        return new Frame<V>(src);
+    }
+
+    /**
+     * Creates a control flow graph edge. The default implementation of this
+     * method does nothing. It can be overriden in order to construct the
+     * control flow graph of a method (this method is called by the
+     * {@link #analyze analyze} method during its visit of the method's code).
+     *
+     * @param insn an instruction index.
+     * @param successor index of a successor instruction.
+     */
+    protected void newControlFlowEdge(final int insn, final int successor) {
+    }
+
+    /**
+     * Creates a control flow graph edge corresponding to an exception handler.
+     * The default implementation of this method does nothing. It can be
+     * overridden in order to construct the control flow graph of a method (this
+     * method is called by the {@link #analyze analyze} method during its visit
+     * of the method's code).
+     *
+     * @param insn an instruction index.
+     * @param successor index of a successor instruction.
+     * @return true if this edge must be considered in the data flow analysis
+     *         performed by this analyzer, or false otherwise. The default
+     *         implementation of this method always returns true.
+     */
+    protected boolean newControlFlowExceptionEdge(
+        final int insn,
+        final int successor)
+    {
+        return true;
+    }
+
+    /**
+     * Creates a control flow graph edge corresponding to an exception handler.
+     * The default implementation of this method delegates to
+     * {@link #newControlFlowExceptionEdge(int, int)
+     * newControlFlowExceptionEdge(int, int)}. It can be overridden in order to
+     * construct the control flow graph of a method (this method is called by
+     * the {@link #analyze analyze} method during its visit of the method's
+     * code).
+     *
+     * @param insn an instruction index.
+     * @param tcb TryCatchBlockNode corresponding to this edge.
+     * @return true if this edge must be considered in the data flow analysis
+     *         performed by this analyzer, or false otherwise. The default
+     *         implementation of this method delegates to
+     *         {@link #newControlFlowExceptionEdge(int, int)
+     *         newControlFlowExceptionEdge(int, int)}.
+     */
+    protected boolean newControlFlowExceptionEdge(
+        final int insn,
+        final TryCatchBlockNode tcb)
+    {
+        return newControlFlowExceptionEdge(insn, insns.indexOf(tcb.handler));
+    }
+
+    // -------------------------------------------------------------------------
+
+    private void merge(
+        final int insn,
+        final Frame<V> frame,
+        final Subroutine subroutine) throws AnalyzerException
+    {
+        Frame<V> oldFrame = frames[insn];
+        Subroutine oldSubroutine = subroutines[insn];
+        boolean changes;
+
+        if (oldFrame == null) {
+            frames[insn] = newFrame(frame);
+            changes = true;
+        } else {
+            changes = oldFrame.merge(frame, interpreter);
+        }
+
+        if (oldSubroutine == null) {
+            if (subroutine != null) {
+                subroutines[insn] = subroutine.copy();
+                changes = true;
+            }
+        } else {
+            if (subroutine != null) {
+                changes |= oldSubroutine.merge(subroutine);
+            }
+        }
+        if (changes && !queued[insn]) {
+            queued[insn] = true;
+            queue[top++] = insn;
+        }
+    }
+
+    private void merge(
+        final int insn,
+        final Frame<V> beforeJSR,
+        final Frame<V> afterRET,
+        final Subroutine subroutineBeforeJSR,
+        final boolean[] access) throws AnalyzerException
+    {
+        Frame<V> oldFrame = frames[insn];
+        Subroutine oldSubroutine = subroutines[insn];
+        boolean changes;
+
+        afterRET.merge(beforeJSR, access);
+
+        if (oldFrame == null) {
+            frames[insn] = newFrame(afterRET);
+            changes = true;
+        } else {
+            changes = oldFrame.merge(afterRET, interpreter);
+        }
+
+        if (oldSubroutine != null && subroutineBeforeJSR != null) {
+            changes |= oldSubroutine.merge(subroutineBeforeJSR);
+        }
+        if (changes && !queued[insn]) {
+            queued[insn] = true;
+            queue[top++] = insn;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/AnalyzerException.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,93 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+
+/**
+ * Thrown if a problem occurs during the analysis of a method.
+ *
+ * @author Bing Ran
+ * @author Eric Bruneton
+ */
+public class AnalyzerException extends Exception {
+
+    public final AbstractInsnNode node;
+
+    public AnalyzerException(final AbstractInsnNode node, final String msg) {
+        super(msg);
+        this.node = node;
+    }
+
+    public AnalyzerException(final AbstractInsnNode node, final String msg, final Throwable exception) {
+        super(msg, exception);
+        this.node = node;
+    }
+
+    public AnalyzerException(
+        final AbstractInsnNode node,
+        final String msg,
+        final Object expected,
+        final Value encountered)
+    {
+        super((msg == null ? "Expected " : msg + ": expected ") + expected
+                + ", but found " + encountered);
+        this.node = node;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/BasicInterpreter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,394 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+import jdk.internal.org.objectweb.asm.tree.FieldInsnNode;
+import jdk.internal.org.objectweb.asm.tree.IntInsnNode;
+import jdk.internal.org.objectweb.asm.tree.InvokeDynamicInsnNode;
+import jdk.internal.org.objectweb.asm.tree.LdcInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MethodInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MultiANewArrayInsnNode;
+import jdk.internal.org.objectweb.asm.tree.TypeInsnNode;
+
+/**
+ * An {@link Interpreter} for {@link BasicValue} values.
+ *
+ * @author Eric Bruneton
+ * @author Bing Ran
+ */
+public class BasicInterpreter extends Interpreter<BasicValue> implements
+        Opcodes
+{
+
+    public BasicInterpreter() {
+        super(ASM4);
+    }
+
+    protected BasicInterpreter(final int api) {
+        super(api);
+    }
+
+    @Override
+    public BasicValue newValue(final Type type) {
+        if (type == null) {
+            return BasicValue.UNINITIALIZED_VALUE;
+        }
+        switch (type.getSort()) {
+            case Type.VOID:
+                return null;
+            case Type.BOOLEAN:
+            case Type.CHAR:
+            case Type.BYTE:
+            case Type.SHORT:
+            case Type.INT:
+                return BasicValue.INT_VALUE;
+            case Type.FLOAT:
+                return BasicValue.FLOAT_VALUE;
+            case Type.LONG:
+                return BasicValue.LONG_VALUE;
+            case Type.DOUBLE:
+                return BasicValue.DOUBLE_VALUE;
+            case Type.ARRAY:
+            case Type.OBJECT:
+                return BasicValue.REFERENCE_VALUE;
+            default:
+                throw new Error("Internal error");
+        }
+    }
+
+    @Override
+    public BasicValue newOperation(final AbstractInsnNode insn)
+            throws AnalyzerException
+    {
+        switch (insn.getOpcode()) {
+            case ACONST_NULL:
+                return newValue(Type.getObjectType("null"));
+            case ICONST_M1:
+            case ICONST_0:
+            case ICONST_1:
+            case ICONST_2:
+            case ICONST_3:
+            case ICONST_4:
+            case ICONST_5:
+                return BasicValue.INT_VALUE;
+            case LCONST_0:
+            case LCONST_1:
+                return BasicValue.LONG_VALUE;
+            case FCONST_0:
+            case FCONST_1:
+            case FCONST_2:
+                return BasicValue.FLOAT_VALUE;
+            case DCONST_0:
+            case DCONST_1:
+                return BasicValue.DOUBLE_VALUE;
+            case BIPUSH:
+            case SIPUSH:
+                return BasicValue.INT_VALUE;
+            case LDC:
+                Object cst = ((LdcInsnNode) insn).cst;
+                if (cst instanceof Integer) {
+                    return BasicValue.INT_VALUE;
+                } else if (cst instanceof Float) {
+                    return BasicValue.FLOAT_VALUE;
+                } else if (cst instanceof Long) {
+                    return BasicValue.LONG_VALUE;
+                } else if (cst instanceof Double) {
+                    return BasicValue.DOUBLE_VALUE;
+                } else if (cst instanceof String) {
+                    return newValue(Type.getObjectType("java/lang/String"));
+                } else if (cst instanceof Type) {
+                    int sort = ((Type) cst).getSort();
+                    if (sort == Type.OBJECT || sort == Type.ARRAY) {
+                        return newValue(Type.getObjectType("java/lang/Class"));
+                    } else if (sort == Type.METHOD) {
+                        return newValue(Type.getObjectType("java/lang/invoke/MethodType"));
+                    } else {
+                        throw new IllegalArgumentException("Illegal LDC constant " + cst);
+                    }
+                } else if (cst instanceof Handle) {
+                    return newValue(Type.getObjectType("java/lang/invoke/MethodHandle"));
+                } else {
+                    throw new IllegalArgumentException("Illegal LDC constant " + cst);
+                }
+            case JSR:
+                return BasicValue.RETURNADDRESS_VALUE;
+            case GETSTATIC:
+                return newValue(Type.getType(((FieldInsnNode) insn).desc));
+            case NEW:
+                return newValue(Type.getObjectType(((TypeInsnNode) insn).desc));
+            default:
+                throw new Error("Internal error.");
+        }
+    }
+
+    @Override
+    public BasicValue copyOperation(final AbstractInsnNode insn, final BasicValue value)
+            throws AnalyzerException
+    {
+        return value;
+    }
+
+    @Override
+    public BasicValue unaryOperation(final AbstractInsnNode insn, final BasicValue value)
+            throws AnalyzerException
+    {
+        switch (insn.getOpcode()) {
+            case INEG:
+            case IINC:
+            case L2I:
+            case F2I:
+            case D2I:
+            case I2B:
+            case I2C:
+            case I2S:
+                return BasicValue.INT_VALUE;
+            case FNEG:
+            case I2F:
+            case L2F:
+            case D2F:
+                return BasicValue.FLOAT_VALUE;
+            case LNEG:
+            case I2L:
+            case F2L:
+            case D2L:
+                return BasicValue.LONG_VALUE;
+            case DNEG:
+            case I2D:
+            case L2D:
+            case F2D:
+                return BasicValue.DOUBLE_VALUE;
+            case IFEQ:
+            case IFNE:
+            case IFLT:
+            case IFGE:
+            case IFGT:
+            case IFLE:
+            case TABLESWITCH:
+            case LOOKUPSWITCH:
+            case IRETURN:
+            case LRETURN:
+            case FRETURN:
+            case DRETURN:
+            case ARETURN:
+            case PUTSTATIC:
+                return null;
+            case GETFIELD:
+                return newValue(Type.getType(((FieldInsnNode) insn).desc));
+            case NEWARRAY:
+                switch (((IntInsnNode) insn).operand) {
+                    case T_BOOLEAN:
+                        return newValue(Type.getType("[Z"));
+                    case T_CHAR:
+                        return newValue(Type.getType("[C"));
+                    case T_BYTE:
+                        return newValue(Type.getType("[B"));
+                    case T_SHORT:
+                        return newValue(Type.getType("[S"));
+                    case T_INT:
+                        return newValue(Type.getType("[I"));
+                    case T_FLOAT:
+                        return newValue(Type.getType("[F"));
+                    case T_DOUBLE:
+                        return newValue(Type.getType("[D"));
+                    case T_LONG:
+                        return newValue(Type.getType("[J"));
+                    default:
+                        throw new AnalyzerException(insn, "Invalid array type");
+                }
+            case ANEWARRAY:
+                String desc = ((TypeInsnNode) insn).desc;
+                return newValue(Type.getType("[" + Type.getObjectType(desc)));
+            case ARRAYLENGTH:
+                return BasicValue.INT_VALUE;
+            case ATHROW:
+                return null;
+            case CHECKCAST:
+                desc = ((TypeInsnNode) insn).desc;
+                return newValue(Type.getObjectType(desc));
+            case INSTANCEOF:
+                return BasicValue.INT_VALUE;
+            case MONITORENTER:
+            case MONITOREXIT:
+            case IFNULL:
+            case IFNONNULL:
+                return null;
+            default:
+                throw new Error("Internal error.");
+        }
+    }
+
+    @Override
+    public BasicValue binaryOperation(
+        final AbstractInsnNode insn,
+        final BasicValue value1,
+        final BasicValue value2) throws AnalyzerException
+    {
+        switch (insn.getOpcode()) {
+            case IALOAD:
+            case BALOAD:
+            case CALOAD:
+            case SALOAD:
+            case IADD:
+            case ISUB:
+            case IMUL:
+            case IDIV:
+            case IREM:
+            case ISHL:
+            case ISHR:
+            case IUSHR:
+            case IAND:
+            case IOR:
+            case IXOR:
+                return BasicValue.INT_VALUE;
+            case FALOAD:
+            case FADD:
+            case FSUB:
+            case FMUL:
+            case FDIV:
+            case FREM:
+                return BasicValue.FLOAT_VALUE;
+            case LALOAD:
+            case LADD:
+            case LSUB:
+            case LMUL:
+            case LDIV:
+            case LREM:
+            case LSHL:
+            case LSHR:
+            case LUSHR:
+            case LAND:
+            case LOR:
+            case LXOR:
+                return BasicValue.LONG_VALUE;
+            case DALOAD:
+            case DADD:
+            case DSUB:
+            case DMUL:
+            case DDIV:
+            case DREM:
+                return BasicValue.DOUBLE_VALUE;
+            case AALOAD:
+                return BasicValue.REFERENCE_VALUE;
+            case LCMP:
+            case FCMPL:
+            case FCMPG:
+            case DCMPL:
+            case DCMPG:
+                return BasicValue.INT_VALUE;
+            case IF_ICMPEQ:
+            case IF_ICMPNE:
+            case IF_ICMPLT:
+            case IF_ICMPGE:
+            case IF_ICMPGT:
+            case IF_ICMPLE:
+            case IF_ACMPEQ:
+            case IF_ACMPNE:
+            case PUTFIELD:
+                return null;
+            default:
+                throw new Error("Internal error.");
+        }
+    }
+
+    @Override
+    public BasicValue ternaryOperation(
+        final AbstractInsnNode insn,
+        final BasicValue value1,
+        final BasicValue value2,
+        final BasicValue value3) throws AnalyzerException
+    {
+        return null;
+    }
+
+    @Override
+    public BasicValue naryOperation(final AbstractInsnNode insn, final List<? extends BasicValue> values)
+            throws AnalyzerException
+    {
+        int opcode = insn.getOpcode();
+        if (opcode == MULTIANEWARRAY) {
+            return newValue(Type.getType(((MultiANewArrayInsnNode) insn).desc));
+        } else if (opcode == INVOKEDYNAMIC){
+            return newValue(Type.getReturnType(((InvokeDynamicInsnNode) insn).desc));
+        } else {
+            return newValue(Type.getReturnType(((MethodInsnNode) insn).desc));
+        }
+    }
+
+    @Override
+    public void returnOperation(
+        final AbstractInsnNode insn,
+        final BasicValue value,
+        final BasicValue expected) throws AnalyzerException
+    {
+    }
+
+    @Override
+    public BasicValue merge(final BasicValue v, final BasicValue w) {
+        if (!v.equals(w)) {
+            return BasicValue.UNINITIALIZED_VALUE;
+        }
+        return v;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/BasicValue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,137 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link Value} that is represented by its type in a seven types type system.
+ * This type system distinguishes the UNINITIALZED, INT, FLOAT, LONG, DOUBLE,
+ * REFERENCE and RETURNADDRESS types.
+ *
+ * @author Eric Bruneton
+ */
+public class BasicValue implements Value {
+
+    public static final BasicValue UNINITIALIZED_VALUE = new BasicValue(null);
+
+    public static final BasicValue INT_VALUE = new BasicValue(Type.INT_TYPE);
+
+    public static final BasicValue FLOAT_VALUE = new BasicValue(Type.FLOAT_TYPE);
+
+    public static final BasicValue LONG_VALUE = new BasicValue(Type.LONG_TYPE);
+
+    public static final BasicValue DOUBLE_VALUE = new BasicValue(Type.DOUBLE_TYPE);
+
+    public static final BasicValue REFERENCE_VALUE = new BasicValue(Type.getObjectType("java/lang/Object"));
+
+    public static final BasicValue RETURNADDRESS_VALUE = new BasicValue(Type.VOID_TYPE);
+
+    private final Type type;
+
+    public BasicValue(final Type type) {
+        this.type = type;
+    }
+
+    public Type getType() {
+        return type;
+    }
+
+    public int getSize() {
+        return type == Type.LONG_TYPE || type == Type.DOUBLE_TYPE ? 2 : 1;
+    }
+
+    public boolean isReference() {
+        return type != null
+                && (type.getSort() == Type.OBJECT || type.getSort() == Type.ARRAY);
+    }
+
+    @Override
+    public boolean equals(final Object value) {
+        if (value == this) {
+            return true;
+        } else if (value instanceof BasicValue) {
+            if (type == null) {
+                return ((BasicValue) value).type == null;
+            } else {
+                return type.equals(((BasicValue) value).type);
+            }
+        } else {
+            return false;
+        }
+    }
+
+    @Override
+    public int hashCode() {
+        return type == null ? 0 : type.hashCode();
+    }
+
+    @Override
+    public String toString() {
+        if (this == UNINITIALIZED_VALUE) {
+            return ".";
+        } else if (this == RETURNADDRESS_VALUE) {
+            return "A";
+        } else if (this == REFERENCE_VALUE) {
+            return "R";
+        } else {
+            return type.getDescriptor();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/BasicVerifier.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,488 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+import jdk.internal.org.objectweb.asm.tree.FieldInsnNode;
+import jdk.internal.org.objectweb.asm.tree.InvokeDynamicInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MethodInsnNode;
+
+/**
+ * An extended {@link BasicInterpreter} that checks that bytecode instructions
+ * are correctly used.
+ *
+ * @author Eric Bruneton
+ * @author Bing Ran
+ */
+public class BasicVerifier extends BasicInterpreter {
+
+    public BasicVerifier() {
+        super(ASM4);
+    }
+
+    protected BasicVerifier(final int api) {
+        super(api);
+    }
+
+    @Override
+    public BasicValue copyOperation(final AbstractInsnNode insn, final BasicValue value)
+            throws AnalyzerException
+    {
+        Value expected;
+        switch (insn.getOpcode()) {
+            case ILOAD:
+            case ISTORE:
+                expected = BasicValue.INT_VALUE;
+                break;
+            case FLOAD:
+            case FSTORE:
+                expected = BasicValue.FLOAT_VALUE;
+                break;
+            case LLOAD:
+            case LSTORE:
+                expected = BasicValue.LONG_VALUE;
+                break;
+            case DLOAD:
+            case DSTORE:
+                expected = BasicValue.DOUBLE_VALUE;
+                break;
+            case ALOAD:
+                if (!value.isReference()) {
+                    throw new AnalyzerException(insn,
+                            null,
+                            "an object reference",
+                            value);
+                }
+                return value;
+            case ASTORE:
+                if (!value.isReference()
+                        && !BasicValue.RETURNADDRESS_VALUE.equals(value))
+                {
+                    throw new AnalyzerException(insn,
+                            null,
+                            "an object reference or a return address",
+                            value);
+                }
+                return value;
+            default:
+                return value;
+        }
+        if (!expected.equals(value)) {
+            throw new AnalyzerException(insn, null, expected, value);
+        }
+        return value;
+    }
+
+    @Override
+    public BasicValue unaryOperation(final AbstractInsnNode insn, final BasicValue value)
+            throws AnalyzerException
+    {
+        BasicValue expected;
+        switch (insn.getOpcode()) {
+            case INEG:
+            case IINC:
+            case I2F:
+            case I2L:
+            case I2D:
+            case I2B:
+            case I2C:
+            case I2S:
+            case IFEQ:
+            case IFNE:
+            case IFLT:
+            case IFGE:
+            case IFGT:
+            case IFLE:
+            case TABLESWITCH:
+            case LOOKUPSWITCH:
+            case IRETURN:
+            case NEWARRAY:
+            case ANEWARRAY:
+                expected = BasicValue.INT_VALUE;
+                break;
+            case FNEG:
+            case F2I:
+            case F2L:
+            case F2D:
+            case FRETURN:
+                expected = BasicValue.FLOAT_VALUE;
+                break;
+            case LNEG:
+            case L2I:
+            case L2F:
+            case L2D:
+            case LRETURN:
+                expected = BasicValue.LONG_VALUE;
+                break;
+            case DNEG:
+            case D2I:
+            case D2F:
+            case D2L:
+            case DRETURN:
+                expected = BasicValue.DOUBLE_VALUE;
+                break;
+            case GETFIELD:
+                expected = newValue(Type.getObjectType(((FieldInsnNode) insn).owner));
+                break;
+            case CHECKCAST:
+                if (!value.isReference()) {
+                    throw new AnalyzerException(insn,
+                            null,
+                            "an object reference",
+                            value);
+                }
+                return super.unaryOperation(insn, value);
+            case ARRAYLENGTH:
+                if (!isArrayValue(value)) {
+                    throw new AnalyzerException(insn,
+                            null,
+                            "an array reference",
+                            value);
+                }
+                return super.unaryOperation(insn, value);
+            case ARETURN:
+            case ATHROW:
+            case INSTANCEOF:
+            case MONITORENTER:
+            case MONITOREXIT:
+            case IFNULL:
+            case IFNONNULL:
+                if (!value.isReference()) {
+                    throw new AnalyzerException(insn,
+                            null,
+                            "an object reference",
+                            value);
+                }
+                return super.unaryOperation(insn, value);
+            case PUTSTATIC:
+                expected = newValue(Type.getType(((FieldInsnNode) insn).desc));
+                break;
+            default:
+                throw new Error("Internal error.");
+        }
+        if (!isSubTypeOf(value, expected)) {
+            throw new AnalyzerException(insn, null, expected, value);
+        }
+        return super.unaryOperation(insn, value);
+    }
+
+    @Override
+    public BasicValue binaryOperation(
+        final AbstractInsnNode insn,
+        final BasicValue value1,
+        final BasicValue value2) throws AnalyzerException
+    {
+        BasicValue expected1;
+        BasicValue expected2;
+        switch (insn.getOpcode()) {
+            case IALOAD:
+                expected1 = newValue(Type.getType("[I"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case BALOAD:
+                if (isSubTypeOf(value1, newValue(Type.getType("[Z")))) {
+                    expected1 = newValue(Type.getType("[Z"));
+                } else {
+                    expected1 = newValue(Type.getType("[B"));
+                }
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case CALOAD:
+                expected1 = newValue(Type.getType("[C"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case SALOAD:
+                expected1 = newValue(Type.getType("[S"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case LALOAD:
+                expected1 = newValue(Type.getType("[J"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case FALOAD:
+                expected1 = newValue(Type.getType("[F"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case DALOAD:
+                expected1 = newValue(Type.getType("[D"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case AALOAD:
+                expected1 = newValue(Type.getType("[Ljava/lang/Object;"));
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case IADD:
+            case ISUB:
+            case IMUL:
+            case IDIV:
+            case IREM:
+            case ISHL:
+            case ISHR:
+            case IUSHR:
+            case IAND:
+            case IOR:
+            case IXOR:
+            case IF_ICMPEQ:
+            case IF_ICMPNE:
+            case IF_ICMPLT:
+            case IF_ICMPGE:
+            case IF_ICMPGT:
+            case IF_ICMPLE:
+                expected1 = BasicValue.INT_VALUE;
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case FADD:
+            case FSUB:
+            case FMUL:
+            case FDIV:
+            case FREM:
+            case FCMPL:
+            case FCMPG:
+                expected1 = BasicValue.FLOAT_VALUE;
+                expected2 = BasicValue.FLOAT_VALUE;
+                break;
+            case LADD:
+            case LSUB:
+            case LMUL:
+            case LDIV:
+            case LREM:
+            case LAND:
+            case LOR:
+            case LXOR:
+            case LCMP:
+                expected1 = BasicValue.LONG_VALUE;
+                expected2 = BasicValue.LONG_VALUE;
+                break;
+            case LSHL:
+            case LSHR:
+            case LUSHR:
+                expected1 = BasicValue.LONG_VALUE;
+                expected2 = BasicValue.INT_VALUE;
+                break;
+            case DADD:
+            case DSUB:
+            case DMUL:
+            case DDIV:
+            case DREM:
+            case DCMPL:
+            case DCMPG:
+                expected1 = BasicValue.DOUBLE_VALUE;
+                expected2 = BasicValue.DOUBLE_VALUE;
+                break;
+            case IF_ACMPEQ:
+            case IF_ACMPNE:
+                expected1 = BasicValue.REFERENCE_VALUE;
+                expected2 = BasicValue.REFERENCE_VALUE;
+                break;
+            case PUTFIELD:
+                FieldInsnNode fin = (FieldInsnNode) insn;
+                expected1 = newValue(Type.getObjectType(fin.owner));
+                expected2 = newValue(Type.getType(fin.desc));
+                break;
+            default:
+                throw new Error("Internal error.");
+        }
+        if (!isSubTypeOf(value1, expected1)) {
+            throw new AnalyzerException(insn, "First argument", expected1, value1);
+        } else if (!isSubTypeOf(value2, expected2)) {
+            throw new AnalyzerException(insn, "Second argument", expected2, value2);
+        }
+        if (insn.getOpcode() == AALOAD) {
+            return getElementValue(value1);
+        } else {
+            return super.binaryOperation(insn, value1, value2);
+        }
+    }
+
+    @Override
+    public BasicValue ternaryOperation(
+        final AbstractInsnNode insn,
+        final BasicValue value1,
+        final BasicValue value2,
+        final BasicValue value3) throws AnalyzerException
+    {
+        BasicValue expected1;
+        BasicValue expected3;
+        switch (insn.getOpcode()) {
+            case IASTORE:
+                expected1 = newValue(Type.getType("[I"));
+                expected3 = BasicValue.INT_VALUE;
+                break;
+            case BASTORE:
+                if (isSubTypeOf(value1, newValue(Type.getType("[Z")))) {
+                    expected1 = newValue(Type.getType("[Z"));
+                } else {
+                    expected1 = newValue(Type.getType("[B"));
+                }
+                expected3 = BasicValue.INT_VALUE;
+                break;
+            case CASTORE:
+                expected1 = newValue(Type.getType("[C"));
+                expected3 = BasicValue.INT_VALUE;
+                break;
+            case SASTORE:
+                expected1 = newValue(Type.getType("[S"));
+                expected3 = BasicValue.INT_VALUE;
+                break;
+            case LASTORE:
+                expected1 = newValue(Type.getType("[J"));
+                expected3 = BasicValue.LONG_VALUE;
+                break;
+            case FASTORE:
+                expected1 = newValue(Type.getType("[F"));
+                expected3 = BasicValue.FLOAT_VALUE;
+                break;
+            case DASTORE:
+                expected1 = newValue(Type.getType("[D"));
+                expected3 = BasicValue.DOUBLE_VALUE;
+                break;
+            case AASTORE:
+                expected1 = value1;
+                expected3 = BasicValue.REFERENCE_VALUE;
+                break;
+            default:
+                throw new Error("Internal error.");
+        }
+        if (!isSubTypeOf(value1, expected1)) {
+            throw new AnalyzerException(insn, "First argument", "a " + expected1
+                    + " array reference", value1);
+        } else if (!BasicValue.INT_VALUE.equals(value2)) {
+            throw new AnalyzerException(insn, "Second argument",
+                    BasicValue.INT_VALUE,
+                    value2);
+        } else if (!isSubTypeOf(value3, expected3)) {
+            throw new AnalyzerException(insn, "Third argument", expected3, value3);
+        }
+        return null;
+    }
+
+    @Override
+    public BasicValue naryOperation(final AbstractInsnNode insn, final List<? extends BasicValue> values)
+            throws AnalyzerException
+    {
+        int opcode = insn.getOpcode();
+        if (opcode == MULTIANEWARRAY) {
+            for (int i = 0; i < values.size(); ++i) {
+                if (!BasicValue.INT_VALUE.equals(values.get(i))) {
+                    throw new AnalyzerException(insn,
+                            null,
+                            BasicValue.INT_VALUE,
+                            values.get(i));
+                }
+            }
+        } else {
+            int i = 0;
+            int j = 0;
+            if (opcode != INVOKESTATIC && opcode != INVOKEDYNAMIC) {
+                Type owner = Type.getObjectType(((MethodInsnNode) insn).owner);
+                if (!isSubTypeOf(values.get(i++), newValue(owner))) {
+                    throw new AnalyzerException(insn, "Method owner",
+                            newValue(owner),
+                            values.get(0));
+                }
+            }
+            String desc = (opcode == INVOKEDYNAMIC)?
+                    ((InvokeDynamicInsnNode) insn).desc:
+                        ((MethodInsnNode) insn).desc;
+            Type[] args = Type.getArgumentTypes(desc);
+            while (i < values.size()) {
+                BasicValue expected = newValue(args[j++]);
+                BasicValue encountered = values.get(i++);
+                if (!isSubTypeOf(encountered, expected)) {
+                    throw new AnalyzerException(insn,
+                            "Argument " + j,
+                            expected,
+                            encountered);
+                }
+            }
+        }
+        return super.naryOperation(insn, values);
+    }
+
+    @Override
+    public void returnOperation(
+        final AbstractInsnNode insn,
+        final BasicValue value,
+        final BasicValue expected) throws AnalyzerException
+    {
+        if (!isSubTypeOf(value, expected)) {
+            throw new AnalyzerException(insn,
+                    "Incompatible return type",
+                    expected,
+                    value);
+        }
+    }
+
+    protected boolean isArrayValue(final BasicValue value) {
+        return value.isReference();
+    }
+
+    protected BasicValue getElementValue(final BasicValue objectArrayValue)
+            throws AnalyzerException
+    {
+        return BasicValue.REFERENCE_VALUE;
+    }
+
+    protected boolean isSubTypeOf(final BasicValue value, final BasicValue expected) {
+        return value.equals(expected);
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/Frame.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,738 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+import jdk.internal.org.objectweb.asm.tree.IincInsnNode;
+import jdk.internal.org.objectweb.asm.tree.InvokeDynamicInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MethodInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MultiANewArrayInsnNode;
+import jdk.internal.org.objectweb.asm.tree.VarInsnNode;
+
+/**
+ * A symbolic execution stack frame. A stack frame contains a set of local
+ * variable slots, and an operand stack. Warning: long and double values are
+ * represented by <i>two</i> slots in local variables, and by <i>one</i> slot
+ * in the operand stack.
+ *
+ * @param <V> type of the Value used for the analysis.
+ *
+ * @author Eric Bruneton
+ */
+public class Frame<V extends Value> {
+
+    /**
+     * The expected return type of the analyzed method, or <tt>null</tt> if the
+     * method returns void.
+     */
+    private V returnValue;
+
+    /**
+     * The local variables and operand stack of this frame.
+     */
+    private V[] values;
+
+    /**
+     * The number of local variables of this frame.
+     */
+    private int locals;
+
+    /**
+     * The number of elements in the operand stack.
+     */
+    private int top;
+
+    /**
+     * Constructs a new frame with the given size.
+     *
+     * @param nLocals the maximum number of local variables of the frame.
+     * @param nStack the maximum stack size of the frame.
+     */
+    public Frame(final int nLocals, final int nStack) {
+        this.values = (V[]) new Value[nLocals + nStack];
+        this.locals = nLocals;
+    }
+
+    /**
+     * Constructs a new frame that is identical to the given frame.
+     *
+     * @param src a frame.
+     */
+    public Frame(final Frame<? extends V> src) {
+        this(src.locals, src.values.length - src.locals);
+        init(src);
+    }
+
+    /**
+     * Copies the state of the given frame into this frame.
+     *
+     * @param src a frame.
+     * @return this frame.
+     */
+    public Frame<V> init(final Frame<? extends V> src) {
+        returnValue = src.returnValue;
+        System.arraycopy(src.values, 0, values, 0, values.length);
+        top = src.top;
+        return this;
+    }
+
+    /**
+     * Sets the expected return type of the analyzed method.
+     *
+     * @param v the expected return type of the analyzed method, or
+     *        <tt>null</tt> if the method returns void.
+     */
+    public void setReturn(final V v) {
+        returnValue = v;
+    }
+
+    /**
+     * Returns the maximum number of local variables of this frame.
+     *
+     * @return the maximum number of local variables of this frame.
+     */
+    public int getLocals() {
+        return locals;
+    }
+
+    /**
+     * Returns the value of the given local variable.
+     *
+     * @param i a local variable index.
+     * @return the value of the given local variable.
+     * @throws IndexOutOfBoundsException if the variable does not exist.
+     */
+    public V getLocal(final int i) throws IndexOutOfBoundsException {
+        if (i >= locals) {
+            throw new IndexOutOfBoundsException("Trying to access an inexistant local variable");
+        }
+        return values[i];
+    }
+
+    /**
+     * Sets the value of the given local variable.
+     *
+     * @param i a local variable index.
+     * @param value the new value of this local variable.
+     * @throws IndexOutOfBoundsException if the variable does not exist.
+     */
+    public void setLocal(final int i, final V value)
+            throws IndexOutOfBoundsException
+    {
+        if (i >= locals) {
+            throw new IndexOutOfBoundsException("Trying to access an inexistant local variable "+i);
+        }
+        values[i] = value;
+    }
+
+    /**
+     * Returns the number of values in the operand stack of this frame. Long and
+     * double values are treated as single values.
+     *
+     * @return the number of values in the operand stack of this frame.
+     */
+    public int getStackSize() {
+        return top;
+    }
+
+    /**
+     * Returns the value of the given operand stack slot.
+     *
+     * @param i the index of an operand stack slot.
+     * @return the value of the given operand stack slot.
+     * @throws IndexOutOfBoundsException if the operand stack slot does not
+     *         exist.
+     */
+    public V getStack(final int i) throws IndexOutOfBoundsException {
+        return values[i + locals];
+    }
+
+    /**
+     * Clears the operand stack of this frame.
+     */
+    public void clearStack() {
+        top = 0;
+    }
+
+    /**
+     * Pops a value from the operand stack of this frame.
+     *
+     * @return the value that has been popped from the stack.
+     * @throws IndexOutOfBoundsException if the operand stack is empty.
+     */
+    public V pop() throws IndexOutOfBoundsException {
+        if (top == 0) {
+            throw new IndexOutOfBoundsException("Cannot pop operand off an empty stack.");
+        }
+        return values[--top + locals];
+    }
+
+    /**
+     * Pushes a value into the operand stack of this frame.
+     *
+     * @param value the value that must be pushed into the stack.
+     * @throws IndexOutOfBoundsException if the operand stack is full.
+     */
+    public void push(final V value) throws IndexOutOfBoundsException {
+        if (top + locals >= values.length) {
+            throw new IndexOutOfBoundsException("Insufficient maximum stack size.");
+        }
+        values[top++ + locals] = value;
+    }
+
+    public void execute(
+        final AbstractInsnNode insn,
+        final Interpreter<V> interpreter) throws AnalyzerException
+    {
+        V value1, value2, value3, value4;
+        List<V> values;
+        int var;
+
+        switch (insn.getOpcode()) {
+            case Opcodes.NOP:
+                break;
+            case Opcodes.ACONST_NULL:
+            case Opcodes.ICONST_M1:
+            case Opcodes.ICONST_0:
+            case Opcodes.ICONST_1:
+            case Opcodes.ICONST_2:
+            case Opcodes.ICONST_3:
+            case Opcodes.ICONST_4:
+            case Opcodes.ICONST_5:
+            case Opcodes.LCONST_0:
+            case Opcodes.LCONST_1:
+            case Opcodes.FCONST_0:
+            case Opcodes.FCONST_1:
+            case Opcodes.FCONST_2:
+            case Opcodes.DCONST_0:
+            case Opcodes.DCONST_1:
+            case Opcodes.BIPUSH:
+            case Opcodes.SIPUSH:
+            case Opcodes.LDC:
+                push(interpreter.newOperation(insn));
+                break;
+            case Opcodes.ILOAD:
+            case Opcodes.LLOAD:
+            case Opcodes.FLOAD:
+            case Opcodes.DLOAD:
+            case Opcodes.ALOAD:
+                push(interpreter.copyOperation(insn,
+                        getLocal(((VarInsnNode) insn).var)));
+                break;
+            case Opcodes.IALOAD:
+            case Opcodes.LALOAD:
+            case Opcodes.FALOAD:
+            case Opcodes.DALOAD:
+            case Opcodes.AALOAD:
+            case Opcodes.BALOAD:
+            case Opcodes.CALOAD:
+            case Opcodes.SALOAD:
+                value2 = pop();
+                value1 = pop();
+                push(interpreter.binaryOperation(insn, value1, value2));
+                break;
+            case Opcodes.ISTORE:
+            case Opcodes.LSTORE:
+            case Opcodes.FSTORE:
+            case Opcodes.DSTORE:
+            case Opcodes.ASTORE:
+                value1 = interpreter.copyOperation(insn, pop());
+                var = ((VarInsnNode) insn).var;
+                setLocal(var, value1);
+                if (value1.getSize() == 2) {
+                    setLocal(var + 1, interpreter.newValue(null));
+                }
+                if (var > 0) {
+                    Value local = getLocal(var - 1);
+                    if (local != null && local.getSize() == 2) {
+                        setLocal(var - 1, interpreter.newValue(null));
+                    }
+                }
+                break;
+            case Opcodes.IASTORE:
+            case Opcodes.LASTORE:
+            case Opcodes.FASTORE:
+            case Opcodes.DASTORE:
+            case Opcodes.AASTORE:
+            case Opcodes.BASTORE:
+            case Opcodes.CASTORE:
+            case Opcodes.SASTORE:
+                value3 = pop();
+                value2 = pop();
+                value1 = pop();
+                interpreter.ternaryOperation(insn, value1, value2, value3);
+                break;
+            case Opcodes.POP:
+                if (pop().getSize() == 2) {
+                    throw new AnalyzerException(insn, "Illegal use of POP");
+                }
+                break;
+            case Opcodes.POP2:
+                if (pop().getSize() == 1) {
+                    if (pop().getSize() != 1) {
+                        throw new AnalyzerException(insn, "Illegal use of POP2");
+                    }
+                }
+                break;
+            case Opcodes.DUP:
+                value1 = pop();
+                if (value1.getSize() != 1) {
+                    throw new AnalyzerException(insn, "Illegal use of DUP");
+                }
+                push(value1);
+                push(interpreter.copyOperation(insn, value1));
+                break;
+            case Opcodes.DUP_X1:
+                value1 = pop();
+                value2 = pop();
+                if (value1.getSize() != 1 || value2.getSize() != 1) {
+                    throw new AnalyzerException(insn, "Illegal use of DUP_X1");
+                }
+                push(interpreter.copyOperation(insn, value1));
+                push(value2);
+                push(value1);
+                break;
+            case Opcodes.DUP_X2:
+                value1 = pop();
+                if (value1.getSize() == 1) {
+                    value2 = pop();
+                    if (value2.getSize() == 1) {
+                        value3 = pop();
+                        if (value3.getSize() == 1) {
+                            push(interpreter.copyOperation(insn, value1));
+                            push(value3);
+                            push(value2);
+                            push(value1);
+                            break;
+                        }
+                    } else {
+                        push(interpreter.copyOperation(insn, value1));
+                        push(value2);
+                        push(value1);
+                        break;
+                    }
+                }
+                throw new AnalyzerException(insn, "Illegal use of DUP_X2");
+            case Opcodes.DUP2:
+                value1 = pop();
+                if (value1.getSize() == 1) {
+                    value2 = pop();
+                    if (value2.getSize() == 1) {
+                        push(value2);
+                        push(value1);
+                        push(interpreter.copyOperation(insn, value2));
+                        push(interpreter.copyOperation(insn, value1));
+                        break;
+                    }
+                } else {
+                    push(value1);
+                    push(interpreter.copyOperation(insn, value1));
+                    break;
+                }
+                throw new AnalyzerException(insn, "Illegal use of DUP2");
+            case Opcodes.DUP2_X1:
+                value1 = pop();
+                if (value1.getSize() == 1) {
+                    value2 = pop();
+                    if (value2.getSize() == 1) {
+                        value3 = pop();
+                        if (value3.getSize() == 1) {
+                            push(interpreter.copyOperation(insn, value2));
+                            push(interpreter.copyOperation(insn, value1));
+                            push(value3);
+                            push(value2);
+                            push(value1);
+                            break;
+                        }
+                    }
+                } else {
+                    value2 = pop();
+                    if (value2.getSize() == 1) {
+                        push(interpreter.copyOperation(insn, value1));
+                        push(value2);
+                        push(value1);
+                        break;
+                    }
+                }
+                throw new AnalyzerException(insn, "Illegal use of DUP2_X1");
+            case Opcodes.DUP2_X2:
+                value1 = pop();
+                if (value1.getSize() == 1) {
+                    value2 = pop();
+                    if (value2.getSize() == 1) {
+                        value3 = pop();
+                        if (value3.getSize() == 1) {
+                            value4 = pop();
+                            if (value4.getSize() == 1) {
+                                push(interpreter.copyOperation(insn, value2));
+                                push(interpreter.copyOperation(insn, value1));
+                                push(value4);
+                                push(value3);
+                                push(value2);
+                                push(value1);
+                                break;
+                            }
+                        } else {
+                            push(interpreter.copyOperation(insn, value2));
+                            push(interpreter.copyOperation(insn, value1));
+                            push(value3);
+                            push(value2);
+                            push(value1);
+                            break;
+                        }
+                    }
+                } else {
+                    value2 = pop();
+                    if (value2.getSize() == 1) {
+                        value3 = pop();
+                        if (value3.getSize() == 1) {
+                            push(interpreter.copyOperation(insn, value1));
+                            push(value3);
+                            push(value2);
+                            push(value1);
+                            break;
+                        }
+                    } else {
+                        push(interpreter.copyOperation(insn, value1));
+                        push(value2);
+                        push(value1);
+                        break;
+                    }
+                }
+                throw new AnalyzerException(insn, "Illegal use of DUP2_X2");
+            case Opcodes.SWAP:
+                value2 = pop();
+                value1 = pop();
+                if (value1.getSize() != 1 || value2.getSize() != 1) {
+                    throw new AnalyzerException(insn, "Illegal use of SWAP");
+                }
+                push(interpreter.copyOperation(insn, value2));
+                push(interpreter.copyOperation(insn, value1));
+                break;
+            case Opcodes.IADD:
+            case Opcodes.LADD:
+            case Opcodes.FADD:
+            case Opcodes.DADD:
+            case Opcodes.ISUB:
+            case Opcodes.LSUB:
+            case Opcodes.FSUB:
+            case Opcodes.DSUB:
+            case Opcodes.IMUL:
+            case Opcodes.LMUL:
+            case Opcodes.FMUL:
+            case Opcodes.DMUL:
+            case Opcodes.IDIV:
+            case Opcodes.LDIV:
+            case Opcodes.FDIV:
+            case Opcodes.DDIV:
+            case Opcodes.IREM:
+            case Opcodes.LREM:
+            case Opcodes.FREM:
+            case Opcodes.DREM:
+                value2 = pop();
+                value1 = pop();
+                push(interpreter.binaryOperation(insn, value1, value2));
+                break;
+            case Opcodes.INEG:
+            case Opcodes.LNEG:
+            case Opcodes.FNEG:
+            case Opcodes.DNEG:
+                push(interpreter.unaryOperation(insn, pop()));
+                break;
+            case Opcodes.ISHL:
+            case Opcodes.LSHL:
+            case Opcodes.ISHR:
+            case Opcodes.LSHR:
+            case Opcodes.IUSHR:
+            case Opcodes.LUSHR:
+            case Opcodes.IAND:
+            case Opcodes.LAND:
+            case Opcodes.IOR:
+            case Opcodes.LOR:
+            case Opcodes.IXOR:
+            case Opcodes.LXOR:
+                value2 = pop();
+                value1 = pop();
+                push(interpreter.binaryOperation(insn, value1, value2));
+                break;
+            case Opcodes.IINC:
+                var = ((IincInsnNode) insn).var;
+                setLocal(var, interpreter.unaryOperation(insn, getLocal(var)));
+                break;
+            case Opcodes.I2L:
+            case Opcodes.I2F:
+            case Opcodes.I2D:
+            case Opcodes.L2I:
+            case Opcodes.L2F:
+            case Opcodes.L2D:
+            case Opcodes.F2I:
+            case Opcodes.F2L:
+            case Opcodes.F2D:
+            case Opcodes.D2I:
+            case Opcodes.D2L:
+            case Opcodes.D2F:
+            case Opcodes.I2B:
+            case Opcodes.I2C:
+            case Opcodes.I2S:
+                push(interpreter.unaryOperation(insn, pop()));
+                break;
+            case Opcodes.LCMP:
+            case Opcodes.FCMPL:
+            case Opcodes.FCMPG:
+            case Opcodes.DCMPL:
+            case Opcodes.DCMPG:
+                value2 = pop();
+                value1 = pop();
+                push(interpreter.binaryOperation(insn, value1, value2));
+                break;
+            case Opcodes.IFEQ:
+            case Opcodes.IFNE:
+            case Opcodes.IFLT:
+            case Opcodes.IFGE:
+            case Opcodes.IFGT:
+            case Opcodes.IFLE:
+                interpreter.unaryOperation(insn, pop());
+                break;
+            case Opcodes.IF_ICMPEQ:
+            case Opcodes.IF_ICMPNE:
+            case Opcodes.IF_ICMPLT:
+            case Opcodes.IF_ICMPGE:
+            case Opcodes.IF_ICMPGT:
+            case Opcodes.IF_ICMPLE:
+            case Opcodes.IF_ACMPEQ:
+            case Opcodes.IF_ACMPNE:
+                value2 = pop();
+                value1 = pop();
+                interpreter.binaryOperation(insn, value1, value2);
+                break;
+            case Opcodes.GOTO:
+                break;
+            case Opcodes.JSR:
+                push(interpreter.newOperation(insn));
+                break;
+            case Opcodes.RET:
+                break;
+            case Opcodes.TABLESWITCH:
+            case Opcodes.LOOKUPSWITCH:
+                interpreter.unaryOperation(insn, pop());
+                break;
+            case Opcodes.IRETURN:
+            case Opcodes.LRETURN:
+            case Opcodes.FRETURN:
+            case Opcodes.DRETURN:
+            case Opcodes.ARETURN:
+                value1 = pop();
+                interpreter.unaryOperation(insn, value1);
+                interpreter.returnOperation(insn, value1, returnValue);
+                break;
+            case Opcodes.RETURN:
+                if (returnValue != null) {
+                    throw new AnalyzerException(insn, "Incompatible return type");
+                }
+                break;
+            case Opcodes.GETSTATIC:
+                push(interpreter.newOperation(insn));
+                break;
+            case Opcodes.PUTSTATIC:
+                interpreter.unaryOperation(insn, pop());
+                break;
+            case Opcodes.GETFIELD:
+                push(interpreter.unaryOperation(insn, pop()));
+                break;
+            case Opcodes.PUTFIELD:
+                value2 = pop();
+                value1 = pop();
+                interpreter.binaryOperation(insn, value1, value2);
+                break;
+            case Opcodes.INVOKEVIRTUAL:
+            case Opcodes.INVOKESPECIAL:
+            case Opcodes.INVOKESTATIC:
+            case Opcodes.INVOKEINTERFACE: {
+                values = new ArrayList<V>();
+                String desc = ((MethodInsnNode) insn).desc;
+                for (int i = Type.getArgumentTypes(desc).length; i > 0; --i) {
+                    values.add(0, pop());
+                }
+                if (insn.getOpcode() != Opcodes.INVOKESTATIC) {
+                    values.add(0, pop());
+                }
+                if (Type.getReturnType(desc) == Type.VOID_TYPE) {
+                    interpreter.naryOperation(insn, values);
+                } else {
+                    push(interpreter.naryOperation(insn, values));
+                }
+                break;
+            }
+            case Opcodes.INVOKEDYNAMIC: {
+                values = new ArrayList<V>();
+                String desc = ((InvokeDynamicInsnNode) insn).desc;
+                for (int i = Type.getArgumentTypes(desc).length; i > 0; --i) {
+                    values.add(0, pop());
+                }
+                if (Type.getReturnType(desc) == Type.VOID_TYPE) {
+                    interpreter.naryOperation(insn, values);
+                } else {
+                    push(interpreter.naryOperation(insn, values));
+                }
+                break;
+            }
+            case Opcodes.NEW:
+                push(interpreter.newOperation(insn));
+                break;
+            case Opcodes.NEWARRAY:
+            case Opcodes.ANEWARRAY:
+            case Opcodes.ARRAYLENGTH:
+                push(interpreter.unaryOperation(insn, pop()));
+                break;
+            case Opcodes.ATHROW:
+                interpreter.unaryOperation(insn, pop());
+                break;
+            case Opcodes.CHECKCAST:
+            case Opcodes.INSTANCEOF:
+                push(interpreter.unaryOperation(insn, pop()));
+                break;
+            case Opcodes.MONITORENTER:
+            case Opcodes.MONITOREXIT:
+                interpreter.unaryOperation(insn, pop());
+                break;
+            case Opcodes.MULTIANEWARRAY:
+                values = new ArrayList<V>();
+                for (int i = ((MultiANewArrayInsnNode) insn).dims; i > 0; --i) {
+                    values.add(0, pop());
+                }
+                push(interpreter.naryOperation(insn, values));
+                break;
+            case Opcodes.IFNULL:
+            case Opcodes.IFNONNULL:
+                interpreter.unaryOperation(insn, pop());
+                break;
+            default:
+                throw new RuntimeException("Illegal opcode "+insn.getOpcode());
+        }
+    }
+
+    /**
+     * Merges this frame with the given frame.
+     *
+     * @param frame a frame.
+     * @param interpreter the interpreter used to merge values.
+     * @return <tt>true</tt> if this frame has been changed as a result of the
+     *         merge operation, or <tt>false</tt> otherwise.
+     * @throws AnalyzerException if the frames have incompatible sizes.
+     */
+    public boolean merge(final Frame<? extends V> frame, final Interpreter<V> interpreter)
+            throws AnalyzerException
+    {
+        if (top != frame.top) {
+            throw new AnalyzerException(null, "Incompatible stack heights");
+        }
+        boolean changes = false;
+        for (int i = 0; i < locals + top; ++i) {
+            V v = interpreter.merge(values[i], frame.values[i]);
+            if (v != values[i]) {
+                values[i] = v;
+                changes |= true;
+            }
+        }
+        return changes;
+    }
+
+    /**
+     * Merges this frame with the given frame (case of a RET instruction).
+     *
+     * @param frame a frame
+     * @param access the local variables that have been accessed by the
+     *        subroutine to which the RET instruction corresponds.
+     * @return <tt>true</tt> if this frame has been changed as a result of the
+     *         merge operation, or <tt>false</tt> otherwise.
+     */
+    public boolean merge(final Frame<? extends V> frame, final boolean[] access) {
+        boolean changes = false;
+        for (int i = 0; i < locals; ++i) {
+            if (!access[i] && !values[i].equals(frame.values[i])) {
+                values[i] = frame.values[i];
+                changes = true;
+            }
+        }
+        return changes;
+    }
+
+    /**
+     * Returns a string representation of this frame.
+     *
+     * @return a string representation of this frame.
+     */
+    @Override
+    public String toString() {
+        StringBuffer b = new StringBuffer();
+        for (int i = 0; i < getLocals(); ++i) {
+            b.append(getLocal(i));
+        }
+        b.append(' ');
+        for (int i = 0; i < getStackSize(); ++i) {
+            b.append(getStack(i).toString());
+        }
+        return b.toString();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/Interpreter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,233 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+
+/**
+ * A semantic bytecode interpreter. More precisely, this interpreter only
+ * manages the computation of values from other values: it does not manage the
+ * transfer of values to or from the stack, and to or from the local variables.
+ * This separation allows a generic bytecode {@link Analyzer} to work with
+ * various semantic interpreters, without needing to duplicate the code to
+ * simulate the transfer of values.
+ *
+ * @param <V> type of the Value used for the analysis.
+ *
+ * @author Eric Bruneton
+ */
+public abstract class Interpreter<V extends Value> {
+
+    protected final int api;
+
+    protected Interpreter(final int api) {
+        this.api = api;
+    }
+
+    /**
+     * Creates a new value that represents the given type.
+     *
+     * Called for method parameters (including <code>this</code>),
+     * exception handler variable and with <code>null</code> type
+     * for variables reserved by long and double types.
+     *
+     * @param type a primitive or reference type, or <tt>null</tt> to
+     *        represent an uninitialized value.
+     * @return a value that represents the given type. The size of the returned
+     *         value must be equal to the size of the given type.
+     */
+    public abstract V newValue(Type type);
+
+    /**
+     * Interprets a bytecode instruction without arguments. This method is
+     * called for the following opcodes:
+     *
+     * ACONST_NULL, ICONST_M1, ICONST_0, ICONST_1, ICONST_2, ICONST_3, ICONST_4,
+     * ICONST_5, LCONST_0, LCONST_1, FCONST_0, FCONST_1, FCONST_2, DCONST_0,
+     * DCONST_1, BIPUSH, SIPUSH, LDC, JSR, GETSTATIC, NEW
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @return the result of the interpretation of the given instruction.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract V newOperation(AbstractInsnNode insn)
+            throws AnalyzerException;
+
+    /**
+     * Interprets a bytecode instruction that moves a value on the stack or to
+     * or from local variables. This method is called for the following opcodes:
+     *
+     * ILOAD, LLOAD, FLOAD, DLOAD, ALOAD, ISTORE, LSTORE, FSTORE, DSTORE,
+     * ASTORE, DUP, DUP_X1, DUP_X2, DUP2, DUP2_X1, DUP2_X2, SWAP
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @param value the value that must be moved by the instruction.
+     * @return the result of the interpretation of the given instruction. The
+     *         returned value must be <tt>equal</tt> to the given value.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract V copyOperation(AbstractInsnNode insn, V value)
+            throws AnalyzerException;
+
+    /**
+     * Interprets a bytecode instruction with a single argument. This method is
+     * called for the following opcodes:
+     *
+     * INEG, LNEG, FNEG, DNEG, IINC, I2L, I2F, I2D, L2I, L2F, L2D, F2I, F2L,
+     * F2D, D2I, D2L, D2F, I2B, I2C, I2S, IFEQ, IFNE, IFLT, IFGE, IFGT, IFLE,
+     * TABLESWITCH, LOOKUPSWITCH, IRETURN, LRETURN, FRETURN, DRETURN, ARETURN,
+     * PUTSTATIC, GETFIELD, NEWARRAY, ANEWARRAY, ARRAYLENGTH, ATHROW, CHECKCAST,
+     * INSTANCEOF, MONITORENTER, MONITOREXIT, IFNULL, IFNONNULL
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @param value the argument of the instruction to be interpreted.
+     * @return the result of the interpretation of the given instruction.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract V unaryOperation(AbstractInsnNode insn, V value)
+            throws AnalyzerException;
+
+    /**
+     * Interprets a bytecode instruction with two arguments. This method is
+     * called for the following opcodes:
+     *
+     * IALOAD, LALOAD, FALOAD, DALOAD, AALOAD, BALOAD, CALOAD, SALOAD, IADD,
+     * LADD, FADD, DADD, ISUB, LSUB, FSUB, DSUB, IMUL, LMUL, FMUL, DMUL, IDIV,
+     * LDIV, FDIV, DDIV, IREM, LREM, FREM, DREM, ISHL, LSHL, ISHR, LSHR, IUSHR,
+     * LUSHR, IAND, LAND, IOR, LOR, IXOR, LXOR, LCMP, FCMPL, FCMPG, DCMPL,
+     * DCMPG, IF_ICMPEQ, IF_ICMPNE, IF_ICMPLT, IF_ICMPGE, IF_ICMPGT, IF_ICMPLE,
+     * IF_ACMPEQ, IF_ACMPNE, PUTFIELD
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @param value1 the first argument of the instruction to be interpreted.
+     * @param value2 the second argument of the instruction to be interpreted.
+     * @return the result of the interpretation of the given instruction.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract V binaryOperation(AbstractInsnNode insn, V value1, V value2)
+            throws AnalyzerException;
+
+    /**
+     * Interprets a bytecode instruction with three arguments. This method is
+     * called for the following opcodes:
+     *
+     * IASTORE, LASTORE, FASTORE, DASTORE, AASTORE, BASTORE, CASTORE, SASTORE
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @param value1 the first argument of the instruction to be interpreted.
+     * @param value2 the second argument of the instruction to be interpreted.
+     * @param value3 the third argument of the instruction to be interpreted.
+     * @return the result of the interpretation of the given instruction.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract V ternaryOperation(
+        AbstractInsnNode insn,
+        V value1,
+        V value2,
+        V value3) throws AnalyzerException;
+
+    /**
+     * Interprets a bytecode instruction with a variable number of arguments.
+     * This method is called for the following opcodes:
+     *
+     * INVOKEVIRTUAL, INVOKESPECIAL, INVOKESTATIC, INVOKEINTERFACE,
+     * MULTIANEWARRAY and INVOKEDYNAMIC
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @param values the arguments of the instruction to be interpreted.
+     * @return the result of the interpretation of the given instruction.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract V naryOperation(
+        AbstractInsnNode insn,
+        List< ? extends V> values) throws AnalyzerException;
+
+    /**
+     * Interprets a bytecode return instruction. This method is called for the
+     * following opcodes:
+     *
+     * IRETURN, LRETURN, FRETURN, DRETURN, ARETURN
+     *
+     * @param insn the bytecode instruction to be interpreted.
+     * @param value the argument of the instruction to be interpreted.
+     * @param expected the expected return type of the analyzed method.
+     * @throws AnalyzerException if an error occured during the interpretation.
+     */
+    public abstract void returnOperation(
+        AbstractInsnNode insn,
+        V value,
+        V expected) throws AnalyzerException;
+
+    /**
+     * Merges two values. The merge operation must return a value that
+     * represents both values (for instance, if the two values are two types,
+     * the merged value must be a common super type of the two types. If the two
+     * values are integer intervals, the merged value must be an interval that
+     * contains the previous ones. Likewise for other types of values).
+     *
+     * @param v a value.
+     * @param w another value.
+     * @return the merged value. If the merged value is equal to <tt>v</tt>,
+     *         this method <i>must</i> return <tt>v</tt>.
+     */
+    public abstract V merge(V v, V w);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/SimpleVerifier.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,358 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * An extended {@link BasicVerifier} that performs more precise verifications.
+ * This verifier computes exact class types, instead of using a single "object
+ * reference" type (as done in the {@link BasicVerifier}).
+ *
+ * @author Eric Bruneton
+ * @author Bing Ran
+ */
+public class SimpleVerifier extends BasicVerifier {
+
+    /**
+     * The class that is verified.
+     */
+    private final Type currentClass;
+
+    /**
+     * The super class of the class that is verified.
+     */
+    private final Type currentSuperClass;
+
+    /**
+     * The interfaces implemented by the class that is verified.
+     */
+    private final List<Type> currentClassInterfaces;
+
+    /**
+     * If the class that is verified is an interface.
+     */
+    private final boolean isInterface;
+
+    /**
+     * The loader to use for referenced classes.
+     */
+    private ClassLoader loader = getClass().getClassLoader();
+
+    /**
+     * Constructs a new {@link SimpleVerifier}.
+     */
+    public SimpleVerifier() {
+        this(null, null, false);
+    }
+
+    /**
+     * Constructs a new {@link SimpleVerifier} to verify a specific class. This
+     * class will not be loaded into the JVM since it may be incorrect.
+     *
+     * @param currentClass the class that is verified.
+     * @param currentSuperClass the super class of the class that is verified.
+     * @param isInterface if the class that is verified is an interface.
+     */
+    public SimpleVerifier(
+        final Type currentClass,
+        final Type currentSuperClass,
+        final boolean isInterface)
+    {
+        this(currentClass, currentSuperClass, null, isInterface);
+    }
+
+    /**
+     * Constructs a new {@link SimpleVerifier} to verify a specific class. This
+     * class will not be loaded into the JVM since it may be incorrect.
+     *
+     * @param currentClass the class that is verified.
+     * @param currentSuperClass the super class of the class that is verified.
+     * @param currentClassInterfaces the interfaces implemented by the class
+     *        that is verified.
+     * @param isInterface if the class that is verified is an interface.
+     */
+    public SimpleVerifier(
+        final Type currentClass,
+        final Type currentSuperClass,
+        final List<Type> currentClassInterfaces,
+        final boolean isInterface)
+    {
+        this(ASM4,
+                currentClass,
+                currentSuperClass,
+                currentClassInterfaces,
+                isInterface);
+    }
+
+    protected SimpleVerifier(
+        final int api,
+        final Type currentClass,
+        final Type currentSuperClass,
+        final List<Type> currentClassInterfaces,
+        final boolean isInterface)
+    {
+        super(api);
+        this.currentClass = currentClass;
+        this.currentSuperClass = currentSuperClass;
+        this.currentClassInterfaces = currentClassInterfaces;
+        this.isInterface = isInterface;
+    }
+
+    /**
+     * Set the <code>ClassLoader</code> which will be used to load referenced
+     * classes. This is useful if you are verifying multiple interdependent
+     * classes.
+     *
+     * @param loader a <code>ClassLoader</code> to use
+     */
+    public void setClassLoader(final ClassLoader loader) {
+        this.loader = loader;
+    }
+
+    @Override
+    public BasicValue newValue(final Type type) {
+        if (type == null) {
+            return BasicValue.UNINITIALIZED_VALUE;
+        }
+
+        boolean isArray = type.getSort() == Type.ARRAY;
+        if (isArray) {
+            switch (type.getElementType().getSort()) {
+                case Type.BOOLEAN:
+                case Type.CHAR:
+                case Type.BYTE:
+                case Type.SHORT:
+                    return new BasicValue(type);
+            }
+        }
+
+        BasicValue v = super.newValue(type);
+        if (BasicValue.REFERENCE_VALUE.equals(v)) {
+            if (isArray) {
+                v = newValue(type.getElementType());
+                String desc = v.getType().getDescriptor();
+                for (int i = 0; i < type.getDimensions(); ++i) {
+                    desc = '[' + desc;
+                }
+                v = new BasicValue(Type.getType(desc));
+            } else {
+                v = new BasicValue(type);
+            }
+        }
+        return v;
+    }
+
+    @Override
+    protected boolean isArrayValue(final BasicValue value) {
+        Type t = value.getType();
+        return t != null
+                && ("Lnull;".equals(t.getDescriptor()) || t.getSort() == Type.ARRAY);
+    }
+
+    @Override
+    protected BasicValue getElementValue(final BasicValue objectArrayValue)
+            throws AnalyzerException
+    {
+        Type arrayType = objectArrayValue.getType();
+        if (arrayType != null) {
+            if (arrayType.getSort() == Type.ARRAY) {
+                return newValue(Type.getType(arrayType.getDescriptor()
+                        .substring(1)));
+            } else if ("Lnull;".equals(arrayType.getDescriptor())) {
+                return objectArrayValue;
+            }
+        }
+        throw new Error("Internal error");
+    }
+
+    @Override
+    protected boolean isSubTypeOf(final BasicValue value, final BasicValue expected) {
+        Type expectedType = expected.getType();
+        Type type = value.getType();
+        switch (expectedType.getSort()) {
+            case Type.INT:
+            case Type.FLOAT:
+            case Type.LONG:
+            case Type.DOUBLE:
+                return type.equals(expectedType);
+            case Type.ARRAY:
+            case Type.OBJECT:
+                if ("Lnull;".equals(type.getDescriptor())) {
+                    return true;
+                } else if (type.getSort() == Type.OBJECT
+                        || type.getSort() == Type.ARRAY)
+                {
+                    return isAssignableFrom(expectedType, type);
+                } else {
+                    return false;
+                }
+            default:
+                throw new Error("Internal error");
+        }
+    }
+
+    @Override
+    public BasicValue merge(final BasicValue v, final BasicValue w) {
+        if (!v.equals(w)) {
+            Type t = v.getType();
+            Type u = w.getType();
+            if (t != null
+                    && (t.getSort() == Type.OBJECT || t.getSort() == Type.ARRAY))
+            {
+                if (u != null
+                        && (u.getSort() == Type.OBJECT || u.getSort() == Type.ARRAY))
+                {
+                    if ("Lnull;".equals(t.getDescriptor())) {
+                        return w;
+                    }
+                    if ("Lnull;".equals(u.getDescriptor())) {
+                        return v;
+                    }
+                    if (isAssignableFrom(t, u)) {
+                        return v;
+                    }
+                    if (isAssignableFrom(u, t)) {
+                        return w;
+                    }
+                    // TODO case of array classes of the same dimension
+                    // TODO should we look also for a common super interface?
+                    // problem: there may be several possible common super
+                    // interfaces
+                    do {
+                        if (t == null || isInterface(t)) {
+                            return BasicValue.REFERENCE_VALUE;
+                        }
+                        t = getSuperClass(t);
+                        if (isAssignableFrom(t, u)) {
+                            return newValue(t);
+                        }
+                    } while (true);
+                }
+            }
+            return BasicValue.UNINITIALIZED_VALUE;
+        }
+        return v;
+    }
+
+    protected boolean isInterface(final Type t) {
+        if (currentClass != null && t.equals(currentClass)) {
+            return isInterface;
+        }
+        return getClass(t).isInterface();
+    }
+
+    protected Type getSuperClass(final Type t) {
+        if (currentClass != null && t.equals(currentClass)) {
+            return currentSuperClass;
+        }
+        Class<?> c = getClass(t).getSuperclass();
+        return c == null ? null : Type.getType(c);
+    }
+
+    protected boolean isAssignableFrom(final Type t, final Type u) {
+        if (t.equals(u)) {
+            return true;
+        }
+        if (currentClass != null && t.equals(currentClass)) {
+            if (getSuperClass(u) == null) {
+                return false;
+            } else {
+                if (isInterface) {
+                    return u.getSort() == Type.OBJECT || u.getSort() == Type.ARRAY;
+                }
+                return isAssignableFrom(t, getSuperClass(u));
+            }
+        }
+        if (currentClass != null && u.equals(currentClass)) {
+            if (isAssignableFrom(t, currentSuperClass)) {
+                return true;
+            }
+            if (currentClassInterfaces != null) {
+                for (int i = 0; i < currentClassInterfaces.size(); ++i) {
+                    Type v = currentClassInterfaces.get(i);
+                    if (isAssignableFrom(t, v)) {
+                        return true;
+                    }
+                }
+            }
+            return false;
+        }
+        Class<?> tc = getClass(t);
+        if (tc.isInterface()) {
+            tc = Object.class;
+        }
+        return tc.isAssignableFrom(getClass(u));
+    }
+
+    protected Class<?> getClass(final Type t) {
+        try {
+            if (t.getSort() == Type.ARRAY) {
+                return Class.forName(t.getDescriptor().replace('/', '.'),
+                        false,
+                        loader);
+            }
+            return Class.forName(t.getClassName(), false, loader);
+        } catch (ClassNotFoundException e) {
+            throw new RuntimeException(e.toString());
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/SmallSet.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,163 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.AbstractSet;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.NoSuchElementException;
+import java.util.Set;
+
+/**
+ * A set of at most two elements.
+ *
+ * @author Eric Bruneton
+ */
+class SmallSet<E> extends AbstractSet<E> implements Iterator<E> {
+
+    // if e1 is null, e2 must be null; otherwise e2 must be different from e1
+
+    E e1, e2;
+
+    static final <T> Set<T> emptySet() {
+        return new SmallSet<T>(null, null);
+    }
+
+    SmallSet(final E e1, final E e2) {
+        this.e1 = e1;
+        this.e2 = e2;
+    }
+
+    // -------------------------------------------------------------------------
+    // Implementation of inherited abstract methods
+    // -------------------------------------------------------------------------
+
+    @Override
+    public Iterator<E> iterator() {
+        return new SmallSet<E>(e1, e2);
+    }
+
+    @Override
+    public int size() {
+        return e1 == null ? 0 : (e2 == null ? 1 : 2);
+    }
+
+    // -------------------------------------------------------------------------
+    // Implementation of the Iterator interface
+    // -------------------------------------------------------------------------
+
+    public boolean hasNext() {
+        return e1 != null;
+    }
+
+    public E next() {
+        if (e1 == null) {
+            throw new NoSuchElementException();
+        }
+        E e = e1;
+        e1 = e2;
+        e2 = null;
+        return e;
+    }
+
+    public void remove() {
+    }
+
+    // -------------------------------------------------------------------------
+    // Utility methods
+    // -------------------------------------------------------------------------
+
+    Set<E> union(final SmallSet<E> s) {
+        if ((s.e1 == e1 && s.e2 == e2) || (s.e1 == e2 && s.e2 == e1)) {
+            return this; // if the two sets are equal, return this
+        }
+        if (s.e1 == null) {
+            return this; // if s is empty, return this
+        }
+        if (e1 == null) {
+            return s; // if this is empty, return s
+        }
+        if (s.e2 == null) { // s contains exactly one element
+            if (e2 == null) {
+                return new SmallSet<E>(e1, s.e1); // necessarily e1 != s.e1
+            } else if (s.e1 == e1 || s.e1 == e2) { // s is included in this
+                return this;
+            }
+        }
+        if (e2 == null) { // this contains exactly one element
+            // if (s.e2 == null) { // cannot happen
+            // return new SmallSet(e1, s.e1); // necessarily e1 != s.e1
+            // } else
+            if (e1 == s.e1 || e1 == s.e2) { // this in included in s
+                return s;
+            }
+        }
+        // here we know that there are at least 3 distinct elements
+        HashSet<E> r = new HashSet<E>(4);
+        r.add(e1);
+        if (e2 != null) {
+            r.add(e2);
+        }
+        r.add(s.e1);
+        if (s.e2 != null) {
+            r.add(s.e2);
+        }
+        return r;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/SourceInterpreter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,235 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+import jdk.internal.org.objectweb.asm.tree.FieldInsnNode;
+import jdk.internal.org.objectweb.asm.tree.InvokeDynamicInsnNode;
+import jdk.internal.org.objectweb.asm.tree.LdcInsnNode;
+import jdk.internal.org.objectweb.asm.tree.MethodInsnNode;
+
+/**
+ * An {@link Interpreter} for {@link SourceValue} values.
+ *
+ * @author Eric Bruneton
+ */
+public class SourceInterpreter extends Interpreter<SourceValue> implements
+        Opcodes
+{
+
+    public SourceInterpreter() {
+        super(ASM4);
+    }
+
+    protected SourceInterpreter(final int api) {
+        super(api);
+    }
+
+    @Override
+    public SourceValue newValue(final Type type) {
+        if (type == Type.VOID_TYPE) {
+            return null;
+        }
+        return new SourceValue(type == null ? 1 : type.getSize());
+    }
+
+    @Override
+    public SourceValue newOperation(final AbstractInsnNode insn) {
+        int size;
+        switch (insn.getOpcode()) {
+            case LCONST_0:
+            case LCONST_1:
+            case DCONST_0:
+            case DCONST_1:
+                size = 2;
+                break;
+            case LDC:
+                Object cst = ((LdcInsnNode) insn).cst;
+                size = cst instanceof Long || cst instanceof Double ? 2 : 1;
+                break;
+            case GETSTATIC:
+                size = Type.getType(((FieldInsnNode) insn).desc).getSize();
+                break;
+            default:
+                size = 1;
+        }
+        return new SourceValue(size, insn);
+    }
+
+    @Override
+    public SourceValue copyOperation(final AbstractInsnNode insn, final SourceValue value) {
+        return new SourceValue(value.getSize(), insn);
+    }
+
+    @Override
+    public SourceValue unaryOperation(final AbstractInsnNode insn, final SourceValue value)
+    {
+        int size;
+        switch (insn.getOpcode()) {
+            case LNEG:
+            case DNEG:
+            case I2L:
+            case I2D:
+            case L2D:
+            case F2L:
+            case F2D:
+            case D2L:
+                size = 2;
+                break;
+            case GETFIELD:
+                size = Type.getType(((FieldInsnNode) insn).desc).getSize();
+                break;
+            default:
+                size = 1;
+        }
+        return new SourceValue(size, insn);
+    }
+
+    @Override
+    public SourceValue binaryOperation(
+        final AbstractInsnNode insn,
+        final SourceValue value1,
+        final SourceValue value2)
+    {
+        int size;
+        switch (insn.getOpcode()) {
+            case LALOAD:
+            case DALOAD:
+            case LADD:
+            case DADD:
+            case LSUB:
+            case DSUB:
+            case LMUL:
+            case DMUL:
+            case LDIV:
+            case DDIV:
+            case LREM:
+            case DREM:
+            case LSHL:
+            case LSHR:
+            case LUSHR:
+            case LAND:
+            case LOR:
+            case LXOR:
+                size = 2;
+                break;
+            default:
+                size = 1;
+        }
+        return new SourceValue(size, insn);
+    }
+
+    @Override
+    public SourceValue ternaryOperation(
+        final AbstractInsnNode insn,
+        final SourceValue value1,
+        final SourceValue value2,
+        final SourceValue value3)
+    {
+        return new SourceValue(1, insn);
+    }
+
+    @Override
+    public SourceValue naryOperation(final AbstractInsnNode insn, final List<? extends SourceValue> values) {
+        int size;
+        int opcode = insn.getOpcode();
+        if (opcode == MULTIANEWARRAY) {
+            size = 1;
+        } else {
+            String desc = (opcode == INVOKEDYNAMIC)?
+                    ((InvokeDynamicInsnNode) insn).desc:
+                    ((MethodInsnNode) insn).desc;
+            size = Type.getReturnType(desc).getSize();
+        }
+        return new SourceValue(size, insn);
+    }
+
+    @Override
+    public void returnOperation(
+        final AbstractInsnNode insn,
+        final SourceValue value,
+        final SourceValue expected)
+    {
+    }
+
+    @Override
+    public SourceValue merge(final SourceValue d, final SourceValue w) {
+        if (d.insns instanceof SmallSet && w.insns instanceof SmallSet) {
+            Set<AbstractInsnNode> s = ((SmallSet<AbstractInsnNode>) d.insns).union((SmallSet<AbstractInsnNode>) w.insns);
+            if (s == d.insns && d.size == w.size) {
+                return d;
+            } else {
+                return new SourceValue(Math.min(d.size, w.size), s);
+            }
+        }
+        if (d.size != w.size || !d.insns.containsAll(w.insns)) {
+            HashSet<AbstractInsnNode> s = new HashSet<AbstractInsnNode>();
+            s.addAll(d.insns);
+            s.addAll(w.insns);
+            return new SourceValue(Math.min(d.size, w.size), s);
+        }
+        return d;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/SourceValue.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,126 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.Set;
+
+import jdk.internal.org.objectweb.asm.tree.AbstractInsnNode;
+
+/**
+ * A {@link Value} that is represented by its type in a two types type system.
+ * This type system distinguishes the ONEWORD and TWOWORDS types.
+ *
+ * @author Eric Bruneton
+ */
+public class SourceValue implements Value {
+
+    /**
+     * The size of this value.
+     */
+    public final int size;
+
+    /**
+     * The instructions that can produce this value. For example, for the Java
+     * code below, the instructions that can produce the value of <tt>i</tt>
+     * at line 5 are the txo ISTORE instructions at line 1 and 3:
+     *
+     * <pre>
+     * 1: i = 0;
+     * 2: if (...) {
+     * 3:   i = 1;
+     * 4: }
+     * 5: return i;
+     * </pre>
+     *
+     * This field is a set of {@link AbstractInsnNode} objects.
+     */
+    public final Set<AbstractInsnNode> insns;
+
+    public SourceValue(final int size) {
+        this(size, SmallSet.<AbstractInsnNode>emptySet());
+    }
+
+    public SourceValue(final int size, final AbstractInsnNode insn) {
+        this.size = size;
+        this.insns = new SmallSet<AbstractInsnNode>(insn, null);
+    }
+
+    public SourceValue(final int size, final Set<AbstractInsnNode> insns) {
+        this.size = size;
+        this.insns = insns;
+    }
+
+    public int getSize() {
+        return size;
+    }
+
+    @Override
+    public boolean equals(final Object value) {
+        if (!(value instanceof SourceValue)) {
+            return false;
+        }
+        SourceValue v = (SourceValue) value;
+        return size == v.size && insns.equals(v.insns);
+    }
+
+    @Override
+    public int hashCode() {
+        return insns.hashCode();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/Subroutine.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,122 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.tree.JumpInsnNode;
+import jdk.internal.org.objectweb.asm.tree.LabelNode;
+
+/**
+ * A method subroutine (corresponds to a JSR instruction).
+ *
+ * @author Eric Bruneton
+ */
+class Subroutine {
+
+    LabelNode start;
+
+    boolean[] access;
+
+    List<JumpInsnNode> callers;
+
+    private Subroutine() {
+    }
+
+    Subroutine(
+        final LabelNode start,
+        final int maxLocals,
+        final JumpInsnNode caller)
+    {
+        this.start = start;
+        this.access = new boolean[maxLocals];
+        this.callers = new ArrayList<JumpInsnNode>();
+        callers.add(caller);
+    }
+
+    public Subroutine copy() {
+        Subroutine result = new Subroutine();
+        result.start = start;
+        result.access = new boolean[access.length];
+        System.arraycopy(access, 0, result.access, 0, access.length);
+        result.callers = new ArrayList<JumpInsnNode>(callers);
+        return result;
+    }
+
+    public boolean merge(final Subroutine subroutine) throws AnalyzerException {
+        boolean changes = false;
+        for (int i = 0; i < access.length; ++i) {
+            if (subroutine.access[i] && !access[i]) {
+                access[i] = true;
+                changes = true;
+            }
+        }
+        if (subroutine.start == start) {
+            for (int i = 0; i < subroutine.callers.size(); ++i) {
+                JumpInsnNode caller = subroutine.callers.get(i);
+                if (!callers.contains(caller)) {
+                    callers.add(caller);
+                    changes = true;
+                }
+            }
+        }
+        return changes;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/tree/analysis/Value.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,74 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.tree.analysis;
+
+/**
+ * An immutable symbolic value for semantic interpretation of bytecode.
+ *
+ * @author Eric Bruneton
+ */
+public interface Value {
+
+    /**
+     * Returns the size of this value in words.
+     *
+     * @return either 1 or 2.
+     */
+    int getSize();
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/ASMifiable.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,82 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Label;
+
+/**
+ * An {@link jdk.internal.org.objectweb.asm.Attribute Attribute} that can print the ASM code
+ * to create an equivalent attribute.
+ *
+ * @author Eugene Kuleshov
+ */
+public interface ASMifiable {
+
+    /**
+     * Prints the ASM code to create an attribute equal to this attribute.
+     *
+     * @param buf a buffer used for printing Java code.
+     * @param varName name of the variable in a printed code used to store
+     *        attribute instance.
+     * @param labelNames map of label instances to their names.
+     */
+    void asmify(StringBuffer buf, String varName, Map<Label, String> labelNames);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/ASMifier.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1268 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.io.FileInputStream;
+import java.io.PrintWriter;
+import java.util.HashMap;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassReader;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * A {@link Printer} that prints the ASM code to generate the classes if visits.
+ *
+ * @author Eric Bruneton
+ */
+public class ASMifier extends Printer {
+
+    /**
+     * The name of the visitor variable in the produced code.
+     */
+    protected final String name;
+
+    /**
+     * Identifier of the annotation visitor variable in the produced code.
+     */
+    protected final int id;
+
+    /**
+     * The label names. This map associates String values to Label keys. It is
+     * used only in ASMifierMethodVisitor.
+     */
+    protected Map<Label, String> labelNames;
+
+    /**
+     * Pseudo access flag used to distinguish class access flags.
+     */
+    private static final int ACCESS_CLASS = 262144;
+
+    /**
+     * Pseudo access flag used to distinguish field access flags.
+     */
+    private static final int ACCESS_FIELD = 524288;
+
+    /**
+     * Pseudo access flag used to distinguish inner class flags.
+     */
+    private static final int ACCESS_INNER = 1048576;
+
+    /**
+     * Constructs a new {@link ASMifier}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the
+     * {@link #ASMifier(int, String, int)} version.
+     */
+    public ASMifier() {
+        this(Opcodes.ASM4, "cw", 0);
+    }
+
+    /**
+     * Constructs a new {@link ASMifier}.
+     *
+     * @param api the ASM API version implemented by this class. Must be one of
+     *        {@link Opcodes#ASM4}.
+     * @param name the name of the visitor variable in the produced code.
+     * @param id identifier of the annotation visitor variable in the produced
+     *        code.
+     */
+    protected ASMifier(final int api, final String name, final int id) {
+        super(api);
+        this.name = name;
+        this.id = id;
+    }
+
+    /**
+     * Prints the ASM source code to generate the given class to the standard
+     * output. <p> Usage: ASMifier [-debug] &lt;binary
+     * class name or class file name&gt;
+     *
+     * @param args the command line arguments.
+     *
+     * @throws Exception if the class cannot be found, or if an IO exception
+     *         occurs.
+     */
+    public static void main(final String[] args) throws Exception {
+        int i = 0;
+        int flags = ClassReader.SKIP_DEBUG;
+
+        boolean ok = true;
+        if (args.length < 1 || args.length > 2) {
+            ok = false;
+        }
+        if (ok && "-debug".equals(args[0])) {
+            i = 1;
+            flags = 0;
+            if (args.length != 2) {
+                ok = false;
+            }
+        }
+        if (!ok) {
+            System.err.println("Prints the ASM code to generate the given class.");
+            System.err.println("Usage: ASMifier [-debug] "
+                    + "<fully qualified class name or class file name>");
+            return;
+        }
+        ClassReader cr;
+        if (args[i].endsWith(".class") || args[i].indexOf('\\') > -1
+                || args[i].indexOf('/') > -1)
+        {
+            cr = new ClassReader(new FileInputStream(args[i]));
+        } else {
+            cr = new ClassReader(args[i]);
+        }
+        cr.accept(new TraceClassVisitor(null,
+                new ASMifier(),
+                new PrintWriter(System.out)), flags);
+    }
+
+    // ------------------------------------------------------------------------
+    // Classes
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        String simpleName;
+        int n = name.lastIndexOf('/');
+        if (n == -1) {
+            simpleName = name;
+        } else {
+            text.add("package asm." + name.substring(0, n).replace('/', '.')
+                    + ";\n");
+            simpleName = name.substring(n + 1);
+        }
+        text.add("import java.util.*;\n");
+        text.add("import jdk.internal.org.objectweb.asm.*;\n");
+        text.add("import jdk.internal.org.objectweb.asm.attrs.*;\n");
+        text.add("public class " + simpleName + "Dump implements Opcodes {\n\n");
+        text.add("public static byte[] dump () throws Exception {\n\n");
+        text.add("ClassWriter cw = new ClassWriter(0);\n");
+        text.add("FieldVisitor fv;\n");
+        text.add("MethodVisitor mv;\n");
+        text.add("AnnotationVisitor av0;\n\n");
+
+        buf.setLength(0);
+        buf.append("cw.visit(");
+        switch (version) {
+            case Opcodes.V1_1:
+                buf.append("V1_1");
+                break;
+            case Opcodes.V1_2:
+                buf.append("V1_2");
+                break;
+            case Opcodes.V1_3:
+                buf.append("V1_3");
+                break;
+            case Opcodes.V1_4:
+                buf.append("V1_4");
+                break;
+            case Opcodes.V1_5:
+                buf.append("V1_5");
+                break;
+            case Opcodes.V1_6:
+                buf.append("V1_6");
+                break;
+            case Opcodes.V1_7:
+                buf.append("V1_7");
+                break;
+            default:
+                buf.append(version);
+                break;
+        }
+        buf.append(", ");
+        appendAccess(access | ACCESS_CLASS);
+        buf.append(", ");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(signature);
+        buf.append(", ");
+        appendConstant(superName);
+        buf.append(", ");
+        if (interfaces != null && interfaces.length > 0) {
+            buf.append("new String[] {");
+            for (int i = 0; i < interfaces.length; ++i) {
+                buf.append(i == 0 ? " " : ", ");
+                appendConstant(interfaces[i]);
+            }
+            buf.append(" }");
+        } else {
+            buf.append("null");
+        }
+        buf.append(");\n\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitSource(final String file, final String debug) {
+        buf.setLength(0);
+        buf.append("cw.visitSource(");
+        appendConstant(file);
+        buf.append(", ");
+        appendConstant(debug);
+        buf.append(");\n\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append("cw.visitOuterClass(");
+        appendConstant(owner);
+        buf.append(", ");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(");\n\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public ASMifier visitClassAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        return visitAnnotation(desc, visible);
+    }
+
+    @Override
+    public void visitClassAttribute(final Attribute attr) {
+        visitAttribute(attr);
+    }
+
+    @Override
+    public void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        buf.setLength(0);
+        buf.append("cw.visitInnerClass(");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(outerName);
+        buf.append(", ");
+        appendConstant(innerName);
+        buf.append(", ");
+        appendAccess(access | ACCESS_INNER);
+        buf.append(");\n\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public ASMifier visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        buf.setLength(0);
+        buf.append("{\n");
+        buf.append("fv = cw.visitField(");
+        appendAccess(access | ACCESS_FIELD);
+        buf.append(", ");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(", ");
+        appendConstant(signature);
+        buf.append(", ");
+        appendConstant(value);
+        buf.append(");\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("fv", 0);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    @Override
+    public ASMifier visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        buf.setLength(0);
+        buf.append("{\n");
+        buf.append("mv = cw.visitMethod(");
+        appendAccess(access);
+        buf.append(", ");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(", ");
+        appendConstant(signature);
+        buf.append(", ");
+        if (exceptions != null && exceptions.length > 0) {
+            buf.append("new String[] {");
+            for (int i = 0; i < exceptions.length; ++i) {
+                buf.append(i == 0 ? " " : ", ");
+                appendConstant(exceptions[i]);
+            }
+            buf.append(" }");
+        } else {
+            buf.append("null");
+        }
+        buf.append(");\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("mv", 0);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    @Override
+    public void visitClassEnd() {
+        text.add("cw.visitEnd();\n\n");
+        text.add("return cw.toByteArray();\n");
+        text.add("}\n");
+        text.add("}\n");
+    }
+
+    // ------------------------------------------------------------------------
+    // Annotations
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(final String name, final Object value) {
+        buf.setLength(0);
+        buf.append("av").append(id).append(".visit(");
+        appendConstant(buf, name);
+        buf.append(", ");
+        appendConstant(buf, value);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitEnum(
+        final String name,
+        final String desc,
+        final String value)
+    {
+        buf.setLength(0);
+        buf.append("av").append(id).append(".visitEnum(");
+        appendConstant(buf, name);
+        buf.append(", ");
+        appendConstant(buf, desc);
+        buf.append(", ");
+        appendConstant(buf, value);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public ASMifier visitAnnotation(
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append("{\n");
+        buf.append("AnnotationVisitor av").append(id + 1).append(" = av");
+        buf.append(id).append(".visitAnnotation(");
+        appendConstant(buf, name);
+        buf.append(", ");
+        appendConstant(buf, desc);
+        buf.append(");\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("av", id + 1);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    @Override
+    public ASMifier visitArray(final String name) {
+        buf.setLength(0);
+        buf.append("{\n");
+        buf.append("AnnotationVisitor av").append(id + 1).append(" = av");
+        buf.append(id).append(".visitArray(");
+        appendConstant(buf, name);
+        buf.append(");\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("av", id + 1);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    @Override
+    public void visitAnnotationEnd() {
+        buf.setLength(0);
+        buf.append("av").append(id).append(".visitEnd();\n");
+        text.add(buf.toString());
+    }
+
+    // ------------------------------------------------------------------------
+    // Fields
+    // ------------------------------------------------------------------------
+
+    @Override
+    public ASMifier visitFieldAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        return visitAnnotation(desc, visible);
+    }
+
+    @Override
+    public void visitFieldAttribute(final Attribute attr) {
+        visitAttribute(attr);
+    }
+
+    @Override
+    public void visitFieldEnd() {
+        buf.setLength(0);
+        buf.append(name).append(".visitEnd();\n");
+        text.add(buf.toString());
+    }
+
+    // ------------------------------------------------------------------------
+    // Methods
+    // ------------------------------------------------------------------------
+
+    @Override
+    public ASMifier visitAnnotationDefault() {
+        buf.setLength(0);
+        buf.append("{\n")
+                .append("av0 = ")
+                .append(name)
+                .append(".visitAnnotationDefault();\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("av", 0);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    @Override
+    public ASMifier visitMethodAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        return visitAnnotation(desc, visible);
+    }
+
+    @Override
+    public ASMifier visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible)
+    {
+        buf.setLength(0);
+        buf.append("{\n")
+                .append("av0 = ").append(name).append(".visitParameterAnnotation(")
+                .append(parameter)
+                .append(", ");
+        appendConstant(desc);
+        buf.append(", ").append(visible).append(");\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("av", 0);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    @Override
+    public void visitMethodAttribute(final Attribute attr) {
+        visitAttribute(attr);
+    }
+
+    @Override
+    public void visitCode() {
+        text.add(name + ".visitCode();\n");
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        buf.setLength(0);
+        switch (type) {
+            case Opcodes.F_NEW:
+            case Opcodes.F_FULL:
+                declareFrameTypes(nLocal, local);
+                declareFrameTypes(nStack, stack);
+                if (type == Opcodes.F_NEW) {
+                    buf.append(name).append(".visitFrame(Opcodes.F_NEW, ");
+                } else {
+                    buf.append(name).append(".visitFrame(Opcodes.F_FULL, ");
+                }
+                buf.append(nLocal).append(", new Object[] {");
+                appendFrameTypes(nLocal, local);
+                buf.append("}, ").append(nStack).append(", new Object[] {");
+                appendFrameTypes(nStack, stack);
+                buf.append('}');
+                break;
+            case Opcodes.F_APPEND:
+                declareFrameTypes(nLocal, local);
+                buf.append(name).append(".visitFrame(Opcodes.F_APPEND,")
+                        .append(nLocal)
+                        .append(", new Object[] {");
+                appendFrameTypes(nLocal, local);
+                buf.append("}, 0, null");
+                break;
+            case Opcodes.F_CHOP:
+                buf.append(name).append(".visitFrame(Opcodes.F_CHOP,")
+                        .append(nLocal)
+                        .append(", null, 0, null");
+                break;
+            case Opcodes.F_SAME:
+                buf.append(name).append(".visitFrame(Opcodes.F_SAME, 0, null, 0, null");
+                break;
+            case Opcodes.F_SAME1:
+                declareFrameTypes(1, stack);
+                buf.append(name).append(".visitFrame(Opcodes.F_SAME1, 0, null, 1, new Object[] {");
+                appendFrameTypes(1, stack);
+                buf.append('}');
+                break;
+        }
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        buf.setLength(0);
+        buf.append(name).append(".visitInsn(").append(OPCODES[opcode]).append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        buf.setLength(0);
+        buf.append(name)
+                .append(".visitIntInsn(")
+                .append(OPCODES[opcode])
+                .append(", ")
+                .append(opcode == Opcodes.NEWARRAY
+                        ? TYPES[operand]
+                        : Integer.toString(operand))
+                .append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        buf.setLength(0);
+        buf.append(name)
+                .append(".visitVarInsn(")
+                .append(OPCODES[opcode])
+                .append(", ")
+                .append(var)
+                .append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        buf.setLength(0);
+        buf.append(name).append(".visitTypeInsn(").append(OPCODES[opcode]).append(", ");
+        appendConstant(type);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append(this.name).append(".visitFieldInsn(").append(OPCODES[opcode]).append(", ");
+        appendConstant(owner);
+        buf.append(", ");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append(this.name).append(".visitMethodInsn(").append(OPCODES[opcode]).append(", ");
+        appendConstant(owner);
+        buf.append(", ");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        buf.setLength(0);
+        buf.append(this.name).append(".visitInvokeDynamicInsn(");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(", ");
+        appendConstant(bsm);
+        buf.append(", new Object[]{");
+        for (int i = 0; i < bsmArgs.length; ++i) {
+            appendConstant(bsmArgs[i]);
+            if (i != bsmArgs.length - 1) {
+                buf.append(", ");
+            }
+        }
+        buf.append("});\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        buf.setLength(0);
+        declareLabel(label);
+        buf.append(name).append(".visitJumpInsn(").append(OPCODES[opcode]).append(", ");
+        appendLabel(label);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        buf.setLength(0);
+        declareLabel(label);
+        buf.append(name).append(".visitLabel(");
+        appendLabel(label);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        buf.setLength(0);
+        buf.append(name).append(".visitLdcInsn(");
+        appendConstant(cst);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        buf.setLength(0);
+        buf.append(name)
+                .append(".visitIincInsn(")
+                .append(var)
+                .append(", ")
+                .append(increment)
+                .append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        buf.setLength(0);
+        for (int i = 0; i < labels.length; ++i) {
+            declareLabel(labels[i]);
+        }
+        declareLabel(dflt);
+
+        buf.append(name)
+                .append(".visitTableSwitchInsn(")
+                .append(min)
+                .append(", ")
+                .append(max)
+                .append(", ");
+        appendLabel(dflt);
+        buf.append(", new Label[] {");
+        for (int i = 0; i < labels.length; ++i) {
+            buf.append(i == 0 ? " " : ", ");
+            appendLabel(labels[i]);
+        }
+        buf.append(" });\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        buf.setLength(0);
+        for (int i = 0; i < labels.length; ++i) {
+            declareLabel(labels[i]);
+        }
+        declareLabel(dflt);
+
+        buf.append(name).append(".visitLookupSwitchInsn(");
+        appendLabel(dflt);
+        buf.append(", new int[] {");
+        for (int i = 0; i < keys.length; ++i) {
+            buf.append(i == 0 ? " " : ", ").append(keys[i]);
+        }
+        buf.append(" }, new Label[] {");
+        for (int i = 0; i < labels.length; ++i) {
+            buf.append(i == 0 ? " " : ", ");
+            appendLabel(labels[i]);
+        }
+        buf.append(" });\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        buf.setLength(0);
+        buf.append(name).append(".visitMultiANewArrayInsn(");
+        appendConstant(desc);
+        buf.append(", ").append(dims).append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type)
+    {
+        buf.setLength(0);
+        declareLabel(start);
+        declareLabel(end);
+        declareLabel(handler);
+        buf.append(name).append(".visitTryCatchBlock(");
+        appendLabel(start);
+        buf.append(", ");
+        appendLabel(end);
+        buf.append(", ");
+        appendLabel(handler);
+        buf.append(", ");
+        appendConstant(type);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        buf.setLength(0);
+        buf.append(this.name).append(".visitLocalVariable(");
+        appendConstant(name);
+        buf.append(", ");
+        appendConstant(desc);
+        buf.append(", ");
+        appendConstant(signature);
+        buf.append(", ");
+        appendLabel(start);
+        buf.append(", ");
+        appendLabel(end);
+        buf.append(", ").append(index).append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLineNumber(final int line, final Label start) {
+        buf.setLength(0);
+        buf.append(name).append(".visitLineNumber(").append(line).append(", ");
+        appendLabel(start);
+        buf.append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        buf.setLength(0);
+        buf.append(name)
+                .append(".visitMaxs(")
+                .append(maxStack)
+                .append(", ")
+                .append(maxLocals)
+                .append(");\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMethodEnd() {
+        buf.setLength(0);
+        buf.append(name).append(".visitEnd();\n");
+        text.add(buf.toString());
+    }
+
+    // ------------------------------------------------------------------------
+    // Common methods
+    // ------------------------------------------------------------------------
+
+    public ASMifier visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        buf.setLength(0);
+        buf.append("{\n")
+                .append("av0 = ")
+                .append(name)
+                .append(".visitAnnotation(");
+        appendConstant(desc);
+        buf.append(", ").append(visible).append(");\n");
+        text.add(buf.toString());
+        ASMifier a = createASMifier("av", 0);
+        text.add(a.getText());
+        text.add("}\n");
+        return a;
+    }
+
+    public void visitAttribute(final Attribute attr) {
+        buf.setLength(0);
+        buf.append("// ATTRIBUTE ").append(attr.type).append('\n');
+        if (attr instanceof ASMifiable) {
+            if (labelNames == null) {
+                labelNames = new HashMap<Label, String>();
+            }
+            buf.append("{\n");
+            ((ASMifiable) attr).asmify(buf, "attr", labelNames);
+            buf.append(name).append(".visitAttribute(attr);\n");
+            buf.append("}\n");
+        }
+        text.add(buf.toString());
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    protected ASMifier createASMifier(final String name, final int id)    {
+        return new ASMifier(Opcodes.ASM4, name, id);
+    }
+
+    /**
+     * Appends a string representation of the given access modifiers to {@link
+     * #buf buf}.
+     *
+     * @param access some access modifiers.
+     */
+    void appendAccess(final int access) {
+        boolean first = true;
+        if ((access & Opcodes.ACC_PUBLIC) != 0) {
+            buf.append("ACC_PUBLIC");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_PRIVATE) != 0) {
+            buf.append("ACC_PRIVATE");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_PROTECTED) != 0) {
+            buf.append("ACC_PROTECTED");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_FINAL) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_FINAL");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_STATIC) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_STATIC");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_SYNCHRONIZED) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            if ((access & ACCESS_CLASS) == 0) {
+                buf.append("ACC_SYNCHRONIZED");
+            } else {
+                buf.append("ACC_SUPER");
+            }
+            first = false;
+        }
+        if ((access & Opcodes.ACC_VOLATILE) != 0
+                && (access & ACCESS_FIELD) != 0)
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_VOLATILE");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_BRIDGE) != 0 && (access & ACCESS_CLASS) == 0
+                && (access & ACCESS_FIELD) == 0)
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_BRIDGE");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_VARARGS) != 0 && (access & ACCESS_CLASS) == 0
+                && (access & ACCESS_FIELD) == 0)
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_VARARGS");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_TRANSIENT) != 0
+                && (access & ACCESS_FIELD) != 0)
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_TRANSIENT");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_NATIVE) != 0 && (access & ACCESS_CLASS) == 0
+                && (access & ACCESS_FIELD) == 0)
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_NATIVE");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_ENUM) != 0
+                && ((access & ACCESS_CLASS) != 0
+                        || (access & ACCESS_FIELD) != 0 || (access & ACCESS_INNER) != 0))
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_ENUM");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_ANNOTATION) != 0
+                && ((access & ACCESS_CLASS) != 0 || (access & ACCESS_INNER) != 0))
+        {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_ANNOTATION");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_ABSTRACT) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_ABSTRACT");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_INTERFACE) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_INTERFACE");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_STRICT) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_STRICT");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_SYNTHETIC) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_SYNTHETIC");
+            first = false;
+        }
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            if (!first) {
+                buf.append(" + ");
+            }
+            buf.append("ACC_DEPRECATED");
+            first = false;
+        }
+        if (first) {
+            buf.append('0');
+        }
+    }
+
+    /**
+     * Appends a string representation of the given constant to the given
+     * buffer.
+     *
+     * @param cst an {@link Integer}, {@link Float}, {@link Long},
+     *        {@link Double} or {@link String} object. May be <tt>null</tt>.
+     */
+    protected void appendConstant(final Object cst) {
+        appendConstant(buf, cst);
+    }
+
+    /**
+     * Appends a string representation of the given constant to the given
+     * buffer.
+     *
+     * @param buf a string buffer.
+     * @param cst an {@link Integer}, {@link Float}, {@link Long},
+     *        {@link Double} or {@link String} object. May be <tt>null</tt>.
+     */
+    static void appendConstant(final StringBuffer buf, final Object cst) {
+        if (cst == null) {
+            buf.append("null");
+        } else if (cst instanceof String) {
+            appendString(buf, (String) cst);
+        } else if (cst instanceof Type) {
+            buf.append("Type.getType(\"");
+            buf.append(((Type) cst).getDescriptor());
+            buf.append("\")");
+        } else if (cst instanceof Handle) {
+            buf.append("new Handle(");
+            Handle h = (Handle) cst;
+            buf.append("Opcodes.").append(HANDLE_TAG[h.getTag()]).append(", \"");
+            buf.append(h.getOwner()).append("\", \"");
+            buf.append(h.getName()).append("\", \"");
+            buf.append(h.getDesc()).append("\")");
+        } else if (cst instanceof Byte) {
+            buf.append("new Byte((byte)").append(cst).append(')');
+        } else if (cst instanceof Boolean) {
+            buf.append(((Boolean) cst).booleanValue() ? "Boolean.TRUE" : "Boolean.FALSE");
+        } else if (cst instanceof Short) {
+            buf.append("new Short((short)").append(cst).append(')');
+        } else if (cst instanceof Character) {
+            int c = ((Character) cst).charValue();
+            buf.append("new Character((char)").append(c).append(')');
+        } else if (cst instanceof Integer) {
+            buf.append("new Integer(").append(cst).append(')');
+        } else if (cst instanceof Float) {
+            buf.append("new Float(\"").append(cst).append("\")");
+        } else if (cst instanceof Long) {
+            buf.append("new Long(").append(cst).append("L)");
+        } else if (cst instanceof Double) {
+            buf.append("new Double(\"").append(cst).append("\")");
+        } else if (cst instanceof byte[]) {
+            byte[] v = (byte[]) cst;
+            buf.append("new byte[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append(v[i]);
+            }
+            buf.append('}');
+        } else if (cst instanceof boolean[]) {
+            boolean[] v = (boolean[]) cst;
+            buf.append("new boolean[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append(v[i]);
+            }
+            buf.append('}');
+        } else if (cst instanceof short[]) {
+            short[] v = (short[]) cst;
+            buf.append("new short[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append("(short)").append(v[i]);
+            }
+            buf.append('}');
+        } else if (cst instanceof char[]) {
+            char[] v = (char[]) cst;
+            buf.append("new char[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",")
+                        .append("(char)")
+                        .append((int) v[i]);
+            }
+            buf.append('}');
+        } else if (cst instanceof int[]) {
+            int[] v = (int[]) cst;
+            buf.append("new int[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append(v[i]);
+            }
+            buf.append('}');
+        } else if (cst instanceof long[]) {
+            long[] v = (long[]) cst;
+            buf.append("new long[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append(v[i]).append('L');
+            }
+            buf.append('}');
+        } else if (cst instanceof float[]) {
+            float[] v = (float[]) cst;
+            buf.append("new float[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append(v[i]).append('f');
+            }
+            buf.append('}');
+        } else if (cst instanceof double[]) {
+            double[] v = (double[]) cst;
+            buf.append("new double[] {");
+            for (int i = 0; i < v.length; i++) {
+                buf.append(i == 0 ? "" : ",").append(v[i]).append('d');
+            }
+            buf.append('}');
+        }
+    }
+
+    private void declareFrameTypes(final int n, final Object[] o) {
+        for (int i = 0; i < n; ++i) {
+            if (o[i] instanceof Label) {
+                declareLabel((Label) o[i]);
+            }
+        }
+    }
+
+    private void appendFrameTypes(final int n, final Object[] o) {
+        for (int i = 0; i < n; ++i) {
+            if (i > 0) {
+                buf.append(", ");
+            }
+            if (o[i] instanceof String) {
+                appendConstant(o[i]);
+            } else if (o[i] instanceof Integer) {
+                switch (((Integer) o[i]).intValue()) {
+                    case 0:
+                        buf.append("Opcodes.TOP");
+                        break;
+                    case 1:
+                        buf.append("Opcodes.INTEGER");
+                        break;
+                    case 2:
+                        buf.append("Opcodes.FLOAT");
+                        break;
+                    case 3:
+                        buf.append("Opcodes.DOUBLE");
+                        break;
+                    case 4:
+                        buf.append("Opcodes.LONG");
+                        break;
+                    case 5:
+                        buf.append("Opcodes.NULL");
+                        break;
+                    case 6:
+                        buf.append("Opcodes.UNINITIALIZED_THIS");
+                        break;
+                }
+            } else {
+                appendLabel((Label) o[i]);
+            }
+        }
+    }
+
+    /**
+     * Appends a declaration of the given label to {@link #buf buf}. This
+     * declaration is of the form "Label lXXX = new Label();". Does nothing if
+     * the given label has already been declared.
+     *
+     * @param l a label.
+     */
+    protected void declareLabel(final Label l) {
+        if (labelNames == null) {
+            labelNames = new HashMap<Label, String>();
+        }
+        String name = labelNames.get(l);
+        if (name == null) {
+            name = "l" + labelNames.size();
+            labelNames.put(l, name);
+            buf.append("Label ").append(name).append(" = new Label();\n");
+        }
+    }
+
+    /**
+     * Appends the name of the given label to {@link #buf buf}. The given label
+     * <i>must</i> already have a name. One way to ensure this is to always
+     * call {@link #declareLabel declared} before calling this method.
+     *
+     * @param l a label.
+     */
+    protected void appendLabel(final Label l) {
+        buf.append(labelNames.get(l));
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/CheckAnnotationAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,171 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+
+/**
+ * An {@link AnnotationVisitor} that checks that its methods are properly used.
+ *
+ * @author Eric Bruneton
+ */
+public class CheckAnnotationAdapter extends AnnotationVisitor {
+
+    private final boolean named;
+
+    private boolean end;
+
+    public CheckAnnotationAdapter(final AnnotationVisitor av) {
+        this(av, true);
+    }
+
+    CheckAnnotationAdapter(final AnnotationVisitor av, final boolean named) {
+        super(Opcodes.ASM4, av);
+        this.named = named;
+    }
+
+    @Override
+    public void visit(final String name, final Object value) {
+        checkEnd();
+        checkName(name);
+        if (!(value instanceof Byte || value instanceof Boolean
+                || value instanceof Character || value instanceof Short
+                || value instanceof Integer || value instanceof Long
+                || value instanceof Float || value instanceof Double
+                || value instanceof String || value instanceof Type
+                || value instanceof byte[] || value instanceof boolean[]
+                || value instanceof char[] || value instanceof short[]
+                || value instanceof int[] || value instanceof long[]
+                || value instanceof float[] || value instanceof double[]))
+        {
+            throw new IllegalArgumentException("Invalid annotation value");
+        }
+        if (value instanceof Type) {
+            int sort = ((Type) value).getSort();
+            if (sort != Type.OBJECT && sort != Type.ARRAY) {
+                throw new IllegalArgumentException("Invalid annotation value");
+            }
+        }
+        if (av != null) {
+            av.visit(name, value);
+        }
+    }
+
+    @Override
+    public void visitEnum(
+        final String name,
+        final String desc,
+        final String value)
+    {
+        checkEnd();
+        checkName(name);
+        CheckMethodAdapter.checkDesc(desc, false);
+        if (value == null) {
+            throw new IllegalArgumentException("Invalid enum value");
+        }
+        if (av != null) {
+            av.visitEnum(name, desc, value);
+        }
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String name,
+        final String desc)
+    {
+        checkEnd();
+        checkName(name);
+        CheckMethodAdapter.checkDesc(desc, false);
+        return new CheckAnnotationAdapter(av == null
+                ? null
+                : av.visitAnnotation(name, desc));
+    }
+
+    @Override
+    public AnnotationVisitor visitArray(final String name) {
+        checkEnd();
+        checkName(name);
+        return new CheckAnnotationAdapter(av == null
+                ? null
+                : av.visitArray(name), false);
+    }
+
+    @Override
+    public void visitEnd() {
+        checkEnd();
+        end = true;
+        if (av != null) {
+            av.visitEnd();
+        }
+    }
+
+    private void checkEnd() {
+        if (end) {
+            throw new IllegalStateException("Cannot call a visit method after visitEnd has been called");
+        }
+    }
+
+    private void checkName(final String name) {
+        if (named && name == null) {
+            throw new IllegalArgumentException("Annotation value name must not be null");
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/CheckClassAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,632 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.io.FileInputStream;
+import java.io.PrintWriter;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassReader;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.ClassNode;
+import jdk.internal.org.objectweb.asm.tree.MethodNode;
+import jdk.internal.org.objectweb.asm.tree.analysis.Analyzer;
+import jdk.internal.org.objectweb.asm.tree.analysis.BasicValue;
+import jdk.internal.org.objectweb.asm.tree.analysis.Frame;
+import jdk.internal.org.objectweb.asm.tree.analysis.SimpleVerifier;
+
+/**
+ * A {@link ClassVisitor} that checks that its methods are properly used. More
+ * precisely this class adapter checks each method call individually, based
+ * <i>only</i> on its arguments, but does <i>not</i> check the <i>sequence</i>
+ * of method calls. For example, the invalid sequence
+ * <tt>visitField(ACC_PUBLIC, "i", "I", null)</tt> <tt>visitField(ACC_PUBLIC,
+ * "i", "D", null)</tt>
+ * will <i>not</i> be detected by this class adapter.
+ *
+ * <p><code>CheckClassAdapter</code> can be also used to verify bytecode
+ * transformations in order to make sure transformed bytecode is sane. For
+ * example:
+ *
+ * <pre>
+ *   InputStream is = ...; // get bytes for the source class
+ *   ClassReader cr = new ClassReader(is);
+ *   ClassWriter cw = new ClassWriter(cr, ClassWriter.COMPUTE_MAXS);
+ *   ClassVisitor cv = new <b>MyClassAdapter</b>(new CheckClassAdapter(cw));
+ *   cr.accept(cv, 0);
+ *
+ *   StringWriter sw = new StringWriter();
+ *   PrintWriter pw = new PrintWriter(sw);
+ *   CheckClassAdapter.verify(new ClassReader(cw.toByteArray()), false, pw);
+ *   assertTrue(sw.toString(), sw.toString().length()==0);
+ * </pre>
+ *
+ * Above code runs transformed bytecode trough the
+ * <code>CheckClassAdapter</code>. It won't be exactly the same verification
+ * as JVM does, but it run data flow analysis for the code of each method and
+ * checks that expectations are met for each method instruction.
+ *
+ * <p>If method bytecode has errors, assertion text will show the erroneous
+ * instruction number and dump of the failed method with information about
+ * locals and stack slot for each instruction. For example (format is -
+ * insnNumber locals : stack):
+ *
+ * <pre>
+ * jdk.internal.org.objectweb.asm.tree.analysis.AnalyzerException: Error at instruction 71: Expected I, but found .
+ *   at jdk.internal.org.objectweb.asm.tree.analysis.Analyzer.analyze(Analyzer.java:289)
+ *   at jdk.internal.org.objectweb.asm.util.CheckClassAdapter.verify(CheckClassAdapter.java:135)
+ * ...
+ * remove()V
+ * 00000 LinkedBlockingQueue$Itr . . . . . . . .  :
+ *   ICONST_0
+ * 00001 LinkedBlockingQueue$Itr . . . . . . . .  : I
+ *   ISTORE 2
+ * 00001 LinkedBlockingQueue$Itr <b>.</b> I . . . . . .  :
+ * ...
+ *
+ * 00071 LinkedBlockingQueue$Itr <b>.</b> I . . . . . .  :
+ *   ILOAD 1
+ * 00072 <b>?</b>
+ *   INVOKESPECIAL java/lang/Integer.<init> (I)V
+ * ...
+ * </pre>
+ *
+ * In the above output you can see that variable 1 loaded by
+ * <code>ILOAD 1</code> instruction at position <code>00071</code> is not
+ * initialized. You can also see that at the beginning of the method (code
+ * inserted by the transformation) variable 2 is initialized.
+ *
+ * <p>Note that when used like that, <code>CheckClassAdapter.verify()</code>
+ * can trigger additional class loading, because it is using
+ * <code>SimpleVerifier</code>.
+ *
+ * @author Eric Bruneton
+ */
+public class CheckClassAdapter extends ClassVisitor {
+
+    /**
+     * The class version number.
+     */
+    private int version;
+
+    /**
+     * <tt>true</tt> if the visit method has been called.
+     */
+    private boolean start;
+
+    /**
+     * <tt>true</tt> if the visitSource method has been called.
+     */
+    private boolean source;
+
+    /**
+     * <tt>true</tt> if the visitOuterClass method has been called.
+     */
+    private boolean outer;
+
+    /**
+     * <tt>true</tt> if the visitEnd method has been called.
+     */
+    private boolean end;
+
+    /**
+     * The already visited labels. This map associate Integer values to Label
+     * keys.
+     */
+    private Map<Label, Integer> labels;
+
+    /**
+     * <tt>true</tt> if the method code must be checked with a BasicVerifier.
+     */
+    private boolean checkDataFlow;
+
+    /**
+     * Checks a given class. <p> Usage: CheckClassAdapter &lt;binary
+     * class name or class file name&gt;
+     *
+     * @param args the command line arguments.
+     *
+     * @throws Exception if the class cannot be found, or if an IO exception
+     *         occurs.
+     */
+    public static void main(final String[] args) throws Exception {
+        if (args.length != 1) {
+            System.err.println("Verifies the given class.");
+            System.err.println("Usage: CheckClassAdapter "
+                    + "<fully qualified class name or class file name>");
+            return;
+        }
+        ClassReader cr;
+        if (args[0].endsWith(".class")) {
+            cr = new ClassReader(new FileInputStream(args[0]));
+        } else {
+            cr = new ClassReader(args[0]);
+        }
+
+        verify(cr, false, new PrintWriter(System.err));
+    }
+
+    /**
+     * Checks a given class.
+     *
+     * @param cr a <code>ClassReader</code> that contains bytecode for the
+     *        analysis.
+     * @param loader a <code>ClassLoader</code> which will be used to load
+     *        referenced classes. This is useful if you are verifiying multiple
+     *        interdependent classes.
+     * @param dump true if bytecode should be printed out not only when errors
+     *        are found.
+     * @param pw write where results going to be printed
+     */
+    public static void verify(
+        final ClassReader cr,
+        final ClassLoader loader,
+        final boolean dump,
+        final PrintWriter pw)
+    {
+        ClassNode cn = new ClassNode();
+        cr.accept(new CheckClassAdapter(cn, false), ClassReader.SKIP_DEBUG);
+
+        Type syperType = cn.superName == null
+                ? null
+                : Type.getObjectType(cn.superName);
+        List<MethodNode> methods = cn.methods;
+
+        List<Type> interfaces = new ArrayList<Type>();
+        for (Iterator<String> i = cn.interfaces.iterator(); i.hasNext();) {
+            interfaces.add(Type.getObjectType(i.next().toString()));
+        }
+
+        for (int i = 0; i < methods.size(); ++i) {
+            MethodNode method = methods.get(i);
+            SimpleVerifier verifier = new SimpleVerifier(Type.getObjectType(cn.name),
+                    syperType,
+                    interfaces,
+                    (cn.access & Opcodes.ACC_INTERFACE) != 0);
+            Analyzer<BasicValue> a = new Analyzer<BasicValue>(verifier);
+            if (loader != null) {
+                verifier.setClassLoader(loader);
+            }
+            try {
+                a.analyze(cn.name, method);
+                if (!dump) {
+                    continue;
+                }
+            } catch (Exception e) {
+                e.printStackTrace(pw);
+            }
+            printAnalyzerResult(method, a, pw);
+        }
+        pw.flush();
+    }
+
+    /**
+     * Checks a given class
+     *
+     * @param cr a <code>ClassReader</code> that contains bytecode for the
+     *        analysis.
+     * @param dump true if bytecode should be printed out not only when errors
+     *        are found.
+     * @param pw write where results going to be printed
+     */
+    public static void verify(
+        final ClassReader cr,
+        final boolean dump,
+        final PrintWriter pw)
+    {
+        verify(cr, null, dump, pw);
+    }
+
+    static void printAnalyzerResult(
+        MethodNode method,
+        Analyzer<BasicValue> a,
+        final PrintWriter pw)
+    {
+        Frame<BasicValue>[] frames = a.getFrames();
+        Textifier t = new Textifier();
+        TraceMethodVisitor mv = new TraceMethodVisitor(t);
+
+        pw.println(method.name + method.desc);
+        for (int j = 0; j < method.instructions.size(); ++j) {
+            method.instructions.get(j).accept(mv);
+
+            StringBuffer s = new StringBuffer();
+            Frame<BasicValue> f = frames[j];
+            if (f == null) {
+                s.append('?');
+            } else {
+                for (int k = 0; k < f.getLocals(); ++k) {
+                    s.append(getShortName(f.getLocal(k).toString()))
+                            .append(' ');
+                }
+                s.append(" : ");
+                for (int k = 0; k < f.getStackSize(); ++k) {
+                    s.append(getShortName(f.getStack(k).toString()))
+                            .append(' ');
+                }
+            }
+            while (s.length() < method.maxStack + method.maxLocals + 1) {
+                s.append(' ');
+            }
+            pw.print(Integer.toString(j + 100000).substring(1));
+            pw.print(" " + s + " : " + t.text.get(t.text.size() - 1));
+        }
+        for (int j = 0; j < method.tryCatchBlocks.size(); ++j) {
+            method.tryCatchBlocks.get(j).accept(mv);
+            pw.print(" " + t.text.get(t.text.size() - 1));
+        }
+        pw.println();
+    }
+
+    private static String getShortName(final String name) {
+        int n = name.lastIndexOf('/');
+        int k = name.length();
+        if (name.charAt(k - 1) == ';') {
+            k--;
+        }
+        return n == -1 ? name : name.substring(n + 1, k);
+    }
+
+    /**
+     * Constructs a new {@link CheckClassAdapter}. <i>Subclasses must not use
+     * this constructor</i>. Instead, they must use the
+     * {@link #CheckClassAdapter(int, ClassVisitor, boolean)} version.
+     *
+     * @param cv the class visitor to which this adapter must delegate calls.
+     */
+    public CheckClassAdapter(final ClassVisitor cv) {
+        this(cv, true);
+    }
+
+    /**
+     * Constructs a new {@link CheckClassAdapter}. <i>Subclasses must not use
+     * this constructor</i>. Instead, they must use the
+     * {@link #CheckClassAdapter(int, ClassVisitor, boolean)} version.
+     *
+     * @param cv the class visitor to which this adapter must delegate calls.
+     * @param checkDataFlow <tt>true</tt> to perform basic data flow checks, or
+     *        <tt>false</tt> to not perform any data flow check (see
+     *        {@link CheckMethodAdapter}). This option requires valid maxLocals
+     *        and maxStack values.
+     */
+    public CheckClassAdapter(final ClassVisitor cv, final boolean checkDataFlow)
+    {
+        this(Opcodes.ASM4, cv, checkDataFlow);
+    }
+
+    /**
+     * Constructs a new {@link CheckClassAdapter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param cv the class visitor to which this adapter must delegate calls.
+     * @param checkDataFlow <tt>true</tt> to perform basic data flow checks, or
+     *        <tt>false</tt> to not perform any data flow check (see
+     *        {@link CheckMethodAdapter}). This option requires valid maxLocals
+     *        and maxStack values.
+     */
+    protected CheckClassAdapter(
+        final int api,
+        final ClassVisitor cv,
+        final boolean checkDataFlow)
+    {
+        super(api, cv);
+        this.labels = new HashMap<Label, Integer>();
+        this.checkDataFlow = checkDataFlow;
+    }
+
+    // ------------------------------------------------------------------------
+    // Implementation of the ClassVisitor interface
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        if (start) {
+            throw new IllegalStateException("visit must be called only once");
+        }
+        start = true;
+        checkState();
+        checkAccess(access, Opcodes.ACC_PUBLIC + Opcodes.ACC_FINAL
+                + Opcodes.ACC_SUPER + Opcodes.ACC_INTERFACE
+                + Opcodes.ACC_ABSTRACT + Opcodes.ACC_SYNTHETIC
+                + Opcodes.ACC_ANNOTATION + Opcodes.ACC_ENUM
+                + Opcodes.ACC_DEPRECATED
+                + 0x40000); // ClassWriter.ACC_SYNTHETIC_ATTRIBUTE
+        if (name == null || !name.endsWith("package-info")) {
+            CheckMethodAdapter.checkInternalName(name, "class name");
+        }
+        if ("java/lang/Object".equals(name)) {
+            if (superName != null) {
+                throw new IllegalArgumentException("The super class name of the Object class must be 'null'");
+            }
+        } else {
+            CheckMethodAdapter.checkInternalName(superName, "super class name");
+        }
+        if (signature != null) {
+            CheckMethodAdapter.checkClassSignature(signature);
+        }
+        if ((access & Opcodes.ACC_INTERFACE) != 0) {
+            if (!"java/lang/Object".equals(superName)) {
+                throw new IllegalArgumentException("The super class name of interfaces must be 'java/lang/Object'");
+            }
+        }
+        if (interfaces != null) {
+            for (int i = 0; i < interfaces.length; ++i) {
+                CheckMethodAdapter.checkInternalName(interfaces[i],
+                        "interface name at index " + i);
+            }
+        }
+        this.version = version;
+        super.visit(version, access, name, signature, superName, interfaces);
+    }
+
+    @Override
+    public void visitSource(final String file, final String debug) {
+        checkState();
+        if (source) {
+            throw new IllegalStateException("visitSource can be called only once.");
+        }
+        source = true;
+        super.visitSource(file, debug);
+    }
+
+    @Override
+    public void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        checkState();
+        if (outer) {
+            throw new IllegalStateException("visitOuterClass can be called only once.");
+        }
+        outer = true;
+        if (owner == null) {
+            throw new IllegalArgumentException("Illegal outer class owner");
+        }
+        if (desc != null) {
+            CheckMethodAdapter.checkMethodDesc(desc);
+        }
+        super.visitOuterClass(owner, name, desc);
+    }
+
+    @Override
+    public void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        checkState();
+        CheckMethodAdapter.checkInternalName(name, "class name");
+        if (outerName != null) {
+            CheckMethodAdapter.checkInternalName(outerName, "outer class name");
+        }
+        if (innerName != null) {
+            CheckMethodAdapter.checkIdentifier(innerName, "inner class name");
+        }
+        checkAccess(access, Opcodes.ACC_PUBLIC + Opcodes.ACC_PRIVATE
+                + Opcodes.ACC_PROTECTED + Opcodes.ACC_STATIC
+                + Opcodes.ACC_FINAL + Opcodes.ACC_INTERFACE
+                + Opcodes.ACC_ABSTRACT + Opcodes.ACC_SYNTHETIC
+                + Opcodes.ACC_ANNOTATION + Opcodes.ACC_ENUM);
+        super.visitInnerClass(name, outerName, innerName, access);
+    }
+
+    @Override
+    public FieldVisitor visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        checkState();
+        checkAccess(access, Opcodes.ACC_PUBLIC + Opcodes.ACC_PRIVATE
+                + Opcodes.ACC_PROTECTED + Opcodes.ACC_STATIC
+                + Opcodes.ACC_FINAL + Opcodes.ACC_VOLATILE
+                + Opcodes.ACC_TRANSIENT + Opcodes.ACC_SYNTHETIC
+                + Opcodes.ACC_ENUM + Opcodes.ACC_DEPRECATED
+                + 0x40000); // ClassWriter.ACC_SYNTHETIC_ATTRIBUTE
+        CheckMethodAdapter.checkUnqualifiedName(version, name, "field name");
+        CheckMethodAdapter.checkDesc(desc, false);
+        if (signature != null) {
+            CheckMethodAdapter.checkFieldSignature(signature);
+        }
+        if (value != null) {
+            CheckMethodAdapter.checkConstant(value);
+        }
+        FieldVisitor av = super.visitField(access, name, desc, signature, value);
+        return new CheckFieldAdapter(av);
+    }
+
+    @Override
+    public MethodVisitor visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        checkState();
+        checkAccess(access, Opcodes.ACC_PUBLIC + Opcodes.ACC_PRIVATE
+                + Opcodes.ACC_PROTECTED + Opcodes.ACC_STATIC
+                + Opcodes.ACC_FINAL + Opcodes.ACC_SYNCHRONIZED
+                + Opcodes.ACC_BRIDGE + Opcodes.ACC_VARARGS + Opcodes.ACC_NATIVE
+                + Opcodes.ACC_ABSTRACT + Opcodes.ACC_STRICT
+                + Opcodes.ACC_SYNTHETIC + Opcodes.ACC_DEPRECATED
+                + 0x40000); // ClassWriter.ACC_SYNTHETIC_ATTRIBUTE
+        CheckMethodAdapter.checkMethodIdentifier(version, name, "method name");
+        CheckMethodAdapter.checkMethodDesc(desc);
+        if (signature != null) {
+            CheckMethodAdapter.checkMethodSignature(signature);
+        }
+        if (exceptions != null) {
+            for (int i = 0; i < exceptions.length; ++i) {
+                CheckMethodAdapter.checkInternalName(exceptions[i],
+                        "exception name at index " + i);
+            }
+        }
+        CheckMethodAdapter cma;
+        if (checkDataFlow) {
+            cma = new CheckMethodAdapter(access,
+                    name,
+                    desc,
+                    super.visitMethod(access, name, desc, signature, exceptions),
+                    labels);
+        } else {
+            cma = new CheckMethodAdapter(super.visitMethod(access,
+                    name,
+                    desc,
+                    signature,
+                    exceptions), labels);
+        }
+        cma.version = version;
+        return cma;
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        checkState();
+        CheckMethodAdapter.checkDesc(desc, false);
+        return new CheckAnnotationAdapter(super.visitAnnotation(desc, visible));
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        checkState();
+        if (attr == null) {
+            throw new IllegalArgumentException("Invalid attribute (must not be null)");
+        }
+        super.visitAttribute(attr);
+    }
+
+    @Override
+    public void visitEnd() {
+        checkState();
+        end = true;
+        super.visitEnd();
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Checks that the visit method has been called and that visitEnd has not
+     * been called.
+     */
+    private void checkState() {
+        if (!start) {
+            throw new IllegalStateException("Cannot visit member before visit has been called.");
+        }
+        if (end) {
+            throw new IllegalStateException("Cannot visit member after visitEnd has been called.");
+        }
+    }
+
+    /**
+     * Checks that the given access flags do not contain invalid flags. This
+     * method also checks that mutually incompatible flags are not set
+     * simultaneously.
+     *
+     * @param access the access flags to be checked
+     * @param possibleAccess the valid access flags.
+     */
+    static void checkAccess(final int access, final int possibleAccess) {
+        if ((access & ~possibleAccess) != 0) {
+            throw new IllegalArgumentException("Invalid access flags: "
+                    + access);
+        }
+        int pub = (access & Opcodes.ACC_PUBLIC) == 0 ? 0 : 1;
+        int pri = (access & Opcodes.ACC_PRIVATE) == 0 ? 0 : 1;
+        int pro = (access & Opcodes.ACC_PROTECTED) == 0 ? 0 : 1;
+        if (pub + pri + pro > 1) {
+            throw new IllegalArgumentException("public private and protected are mutually exclusive: "
+                    + access);
+        }
+        int fin = (access & Opcodes.ACC_FINAL) == 0 ? 0 : 1;
+        int abs = (access & Opcodes.ACC_ABSTRACT) == 0 ? 0 : 1;
+        if (fin + abs > 1) {
+            throw new IllegalArgumentException("final and abstract are mutually exclusive: "
+                    + access);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/CheckFieldAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,126 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link FieldVisitor} that checks that its methods are properly used.
+ */
+public class CheckFieldAdapter extends FieldVisitor {
+
+    private boolean end;
+
+    /**
+     * Constructs a new {@link CheckFieldAdapter}. <i>Subclasses must not use
+     * this constructor</i>. Instead, they must use the
+     * {@link #CheckFieldAdapter(int, FieldVisitor)} version.
+     *
+     * @param fv the field visitor to which this adapter must delegate calls.
+     */
+    public CheckFieldAdapter(final FieldVisitor fv) {
+        this(Opcodes.ASM4, fv);
+    }
+
+    /**
+     * Constructs a new {@link CheckFieldAdapter}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param fv the field visitor to which this adapter must delegate calls.
+     */
+    protected CheckFieldAdapter(final int api, final FieldVisitor fv) {
+        super(api, fv);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        checkEnd();
+        CheckMethodAdapter.checkDesc(desc, false);
+        return new CheckAnnotationAdapter(super.visitAnnotation(desc, visible));
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        checkEnd();
+        if (attr == null) {
+            throw new IllegalArgumentException("Invalid attribute (must not be null)");
+        }
+        super.visitAttribute(attr);
+    }
+
+    @Override
+    public void visitEnd() {
+        checkEnd();
+        end = true;
+        super.visitEnd();
+    }
+
+    private void checkEnd() {
+        if (end) {
+            throw new IllegalStateException("Cannot call a visit method after visitEnd has been called");
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/CheckMethodAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1697 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.io.PrintWriter;
+import java.io.StringWriter;
+import java.lang.reflect.Field;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.tree.MethodNode;
+import jdk.internal.org.objectweb.asm.tree.analysis.Analyzer;
+import jdk.internal.org.objectweb.asm.tree.analysis.BasicValue;
+import jdk.internal.org.objectweb.asm.tree.analysis.BasicVerifier;
+
+/**
+ * A {@link MethodVisitor} that checks that its methods are properly used. More
+ * precisely this method adapter checks each instruction individually, i.e.,
+ * each visit method checks some preconditions based <i>only</i> on its
+ * arguments - such as the fact that the given opcode is correct for a given
+ * visit method. This adapter can also perform some basic data flow checks (more
+ * precisely those that can be performed without the full class hierarchy - see
+ * {@link jdk.internal.org.objectweb.asm.tree.analysis.BasicVerifier}). For instance in a
+ * method whose signature is <tt>void m ()</tt>, the invalid instruction
+ * IRETURN, or the invalid sequence IADD L2I will be detected if the data flow
+ * checks are enabled. These checks are enabled by using the
+ * {@link #CheckMethodAdapter(int,String,String,MethodVisitor,Map)} constructor.
+ * They are not performed if any other constructor is used.
+ *
+ * @author Eric Bruneton
+ */
+public class CheckMethodAdapter extends MethodVisitor {
+
+    /**
+     * The class version number.
+     */
+    public int version;
+
+    /**
+     * <tt>true</tt> if the visitCode method has been called.
+     */
+    private boolean startCode;
+
+    /**
+     * <tt>true</tt> if the visitMaxs method has been called.
+     */
+    private boolean endCode;
+
+    /**
+     * <tt>true</tt> if the visitEnd method has been called.
+     */
+    private boolean endMethod;
+
+    /**
+     * Number of visited instructions.
+     */
+    private int insnCount;
+
+    /**
+     * The already visited labels. This map associate Integer values to pseudo
+     * code offsets.
+     */
+    private final Map<Label, Integer> labels;
+
+    /**
+     * The labels used in this method. Every used label must be visited with
+     * visitLabel before the end of the method (i.e. should be in #labels).
+     */
+    private Set<Label> usedLabels;
+
+    /**
+     * The exception handler ranges. Each pair of list element contains the
+     * start and end labels of an exception handler block.
+     */
+    private List<Label> handlers;
+
+    /**
+     * Code of the visit method to be used for each opcode.
+     */
+    private static final int[] TYPE;
+
+    /**
+     * The Label.status field.
+     */
+    private static Field labelStatusField;
+
+    static {
+        String s = "BBBBBBBBBBBBBBBBCCIAADDDDDAAAAAAAAAAAAAAAAAAAABBBBBBBBDD"
+                + "DDDAAAAAAAAAAAAAAAAAAAABBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB"
+                + "BBBBBBBBBBBBBBBBBBBJBBBBBBBBBBBBBBBBBBBBHHHHHHHHHHHHHHHHD"
+                + "KLBBBBBBFFFFGGGGAECEBBEEBBAMHHAA";
+        TYPE = new int[s.length()];
+        for (int i = 0; i < TYPE.length; ++i) {
+            TYPE[i] = s.charAt(i) - 'A' - 1;
+        }
+    }
+
+    // code to generate the above string
+    // public static void main (String[] args) {
+    // int[] TYPE = new int[] {
+    // 0, //NOP
+    // 0, //ACONST_NULL
+    // 0, //ICONST_M1
+    // 0, //ICONST_0
+    // 0, //ICONST_1
+    // 0, //ICONST_2
+    // 0, //ICONST_3
+    // 0, //ICONST_4
+    // 0, //ICONST_5
+    // 0, //LCONST_0
+    // 0, //LCONST_1
+    // 0, //FCONST_0
+    // 0, //FCONST_1
+    // 0, //FCONST_2
+    // 0, //DCONST_0
+    // 0, //DCONST_1
+    // 1, //BIPUSH
+    // 1, //SIPUSH
+    // 7, //LDC
+    // -1, //LDC_W
+    // -1, //LDC2_W
+    // 2, //ILOAD
+    // 2, //LLOAD
+    // 2, //FLOAD
+    // 2, //DLOAD
+    // 2, //ALOAD
+    // -1, //ILOAD_0
+    // -1, //ILOAD_1
+    // -1, //ILOAD_2
+    // -1, //ILOAD_3
+    // -1, //LLOAD_0
+    // -1, //LLOAD_1
+    // -1, //LLOAD_2
+    // -1, //LLOAD_3
+    // -1, //FLOAD_0
+    // -1, //FLOAD_1
+    // -1, //FLOAD_2
+    // -1, //FLOAD_3
+    // -1, //DLOAD_0
+    // -1, //DLOAD_1
+    // -1, //DLOAD_2
+    // -1, //DLOAD_3
+    // -1, //ALOAD_0
+    // -1, //ALOAD_1
+    // -1, //ALOAD_2
+    // -1, //ALOAD_3
+    // 0, //IALOAD
+    // 0, //LALOAD
+    // 0, //FALOAD
+    // 0, //DALOAD
+    // 0, //AALOAD
+    // 0, //BALOAD
+    // 0, //CALOAD
+    // 0, //SALOAD
+    // 2, //ISTORE
+    // 2, //LSTORE
+    // 2, //FSTORE
+    // 2, //DSTORE
+    // 2, //ASTORE
+    // -1, //ISTORE_0
+    // -1, //ISTORE_1
+    // -1, //ISTORE_2
+    // -1, //ISTORE_3
+    // -1, //LSTORE_0
+    // -1, //LSTORE_1
+    // -1, //LSTORE_2
+    // -1, //LSTORE_3
+    // -1, //FSTORE_0
+    // -1, //FSTORE_1
+    // -1, //FSTORE_2
+    // -1, //FSTORE_3
+    // -1, //DSTORE_0
+    // -1, //DSTORE_1
+    // -1, //DSTORE_2
+    // -1, //DSTORE_3
+    // -1, //ASTORE_0
+    // -1, //ASTORE_1
+    // -1, //ASTORE_2
+    // -1, //ASTORE_3
+    // 0, //IASTORE
+    // 0, //LASTORE
+    // 0, //FASTORE
+    // 0, //DASTORE
+    // 0, //AASTORE
+    // 0, //BASTORE
+    // 0, //CASTORE
+    // 0, //SASTORE
+    // 0, //POP
+    // 0, //POP2
+    // 0, //DUP
+    // 0, //DUP_X1
+    // 0, //DUP_X2
+    // 0, //DUP2
+    // 0, //DUP2_X1
+    // 0, //DUP2_X2
+    // 0, //SWAP
+    // 0, //IADD
+    // 0, //LADD
+    // 0, //FADD
+    // 0, //DADD
+    // 0, //ISUB
+    // 0, //LSUB
+    // 0, //FSUB
+    // 0, //DSUB
+    // 0, //IMUL
+    // 0, //LMUL
+    // 0, //FMUL
+    // 0, //DMUL
+    // 0, //IDIV
+    // 0, //LDIV
+    // 0, //FDIV
+    // 0, //DDIV
+    // 0, //IREM
+    // 0, //LREM
+    // 0, //FREM
+    // 0, //DREM
+    // 0, //INEG
+    // 0, //LNEG
+    // 0, //FNEG
+    // 0, //DNEG
+    // 0, //ISHL
+    // 0, //LSHL
+    // 0, //ISHR
+    // 0, //LSHR
+    // 0, //IUSHR
+    // 0, //LUSHR
+    // 0, //IAND
+    // 0, //LAND
+    // 0, //IOR
+    // 0, //LOR
+    // 0, //IXOR
+    // 0, //LXOR
+    // 8, //IINC
+    // 0, //I2L
+    // 0, //I2F
+    // 0, //I2D
+    // 0, //L2I
+    // 0, //L2F
+    // 0, //L2D
+    // 0, //F2I
+    // 0, //F2L
+    // 0, //F2D
+    // 0, //D2I
+    // 0, //D2L
+    // 0, //D2F
+    // 0, //I2B
+    // 0, //I2C
+    // 0, //I2S
+    // 0, //LCMP
+    // 0, //FCMPL
+    // 0, //FCMPG
+    // 0, //DCMPL
+    // 0, //DCMPG
+    // 6, //IFEQ
+    // 6, //IFNE
+    // 6, //IFLT
+    // 6, //IFGE
+    // 6, //IFGT
+    // 6, //IFLE
+    // 6, //IF_ICMPEQ
+    // 6, //IF_ICMPNE
+    // 6, //IF_ICMPLT
+    // 6, //IF_ICMPGE
+    // 6, //IF_ICMPGT
+    // 6, //IF_ICMPLE
+    // 6, //IF_ACMPEQ
+    // 6, //IF_ACMPNE
+    // 6, //GOTO
+    // 6, //JSR
+    // 2, //RET
+    // 9, //TABLESWITCH
+    // 10, //LOOKUPSWITCH
+    // 0, //IRETURN
+    // 0, //LRETURN
+    // 0, //FRETURN
+    // 0, //DRETURN
+    // 0, //ARETURN
+    // 0, //RETURN
+    // 4, //GETSTATIC
+    // 4, //PUTSTATIC
+    // 4, //GETFIELD
+    // 4, //PUTFIELD
+    // 5, //INVOKEVIRTUAL
+    // 5, //INVOKESPECIAL
+    // 5, //INVOKESTATIC
+    // 5, //INVOKEINTERFACE
+    // -1, //INVOKEDYNAMIC
+    // 3, //NEW
+    // 1, //NEWARRAY
+    // 3, //ANEWARRAY
+    // 0, //ARRAYLENGTH
+    // 0, //ATHROW
+    // 3, //CHECKCAST
+    // 3, //INSTANCEOF
+    // 0, //MONITORENTER
+    // 0, //MONITOREXIT
+    // -1, //WIDE
+    // 11, //MULTIANEWARRAY
+    // 6, //IFNULL
+    // 6, //IFNONNULL
+    // -1, //GOTO_W
+    // -1 //JSR_W
+    // };
+    // for (int i = 0; i < TYPE.length; ++i) {
+    // System.out.print((char)(TYPE[i] + 1 + 'A'));
+    // }
+    // System.out.println();
+    // }
+
+    /**
+     * Constructs a new {@link CheckMethodAdapter} object. This method adapter
+     * will not perform any data flow check (see
+     * {@link #CheckMethodAdapter(int,String,String,MethodVisitor,Map)}).
+     * <i>Subclasses must not use this constructor</i>. Instead, they must use
+     * the {@link #CheckMethodAdapter(int, MethodVisitor, Map)} version.
+     *
+     * @param mv the method visitor to which this adapter must delegate calls.
+     */
+    public CheckMethodAdapter(final MethodVisitor mv) {
+        this(mv, new HashMap<Label, Integer>());
+    }
+
+    /**
+     * Constructs a new {@link CheckMethodAdapter} object. This method adapter
+     * will not perform any data flow check (see
+     * {@link #CheckMethodAdapter(int,String,String,MethodVisitor,Map)}).
+     * <i>Subclasses must not use this constructor</i>. Instead, they must use
+     * the {@link #CheckMethodAdapter(int, MethodVisitor, Map)} version.
+     *
+     * @param mv the method visitor to which this adapter must delegate calls.
+     * @param labels a map of already visited labels (in other methods).
+     */
+    public CheckMethodAdapter(
+        final MethodVisitor mv,
+        final Map<Label, Integer> labels)
+    {
+        this(Opcodes.ASM4, mv, labels);
+    }
+
+    /**
+     * Constructs a new {@link CheckMethodAdapter} object. This method adapter
+     * will not perform any data flow check (see
+     * {@link #CheckMethodAdapter(int,String,String,MethodVisitor,Map)}).
+     *
+     * @param mv the method visitor to which this adapter must delegate calls.
+     * @param labels a map of already visited labels (in other methods).
+     */
+    protected CheckMethodAdapter(
+        final int api,
+        final MethodVisitor mv,
+        final Map<Label, Integer> labels)
+    {
+        super(api, mv);
+        this.labels = labels;
+        this.usedLabels = new HashSet<Label>();
+        this.handlers = new ArrayList<Label>();
+    }
+
+    /**
+     * Constructs a new {@link CheckMethodAdapter} object. This method adapter
+     * will perform basic data flow checks. For instance in a method whose
+     * signature is <tt>void m ()</tt>, the invalid instruction IRETURN, or the
+     * invalid sequence IADD L2I will be detected.
+     *
+     * @param access the method's access flags.
+     * @param name the method's name.
+     * @param desc the method's descriptor (see {@link Type Type}).
+     * @param cmv the method visitor to which this adapter must delegate calls.
+     * @param labels a map of already visited labels (in other methods).
+     */
+    public CheckMethodAdapter(
+        final int access,
+        final String name,
+        final String desc,
+        final MethodVisitor cmv,
+        final Map<Label, Integer> labels)
+    {
+        this(new MethodNode(access, name, desc, null, null) {
+            @Override
+            public void visitEnd() {
+                Analyzer<BasicValue> a = new Analyzer<BasicValue>(new BasicVerifier());
+                try {
+                    a.analyze("dummy", this);
+                } catch (Exception e) {
+                    if (e instanceof IndexOutOfBoundsException
+                            && maxLocals == 0 && maxStack == 0)
+                    {
+                        throw new RuntimeException("Data flow checking option requires valid, non zero maxLocals and maxStack values.");
+                    }
+                    e.printStackTrace();
+                    StringWriter sw = new StringWriter();
+                    PrintWriter pw = new PrintWriter(sw, true);
+                    CheckClassAdapter.printAnalyzerResult(this, a, pw);
+                    pw.close();
+                    throw new RuntimeException(e.getMessage() + ' '
+                            + sw.toString());
+                }
+                accept(cmv);
+            }
+        },
+                labels);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        checkEndMethod();
+        checkDesc(desc, false);
+        return new CheckAnnotationAdapter(super.visitAnnotation(desc, visible));
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotationDefault() {
+        checkEndMethod();
+        return new CheckAnnotationAdapter(super.visitAnnotationDefault(), false);
+    }
+
+    @Override
+    public AnnotationVisitor visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible)
+    {
+        checkEndMethod();
+        checkDesc(desc, false);
+        return new CheckAnnotationAdapter(super.visitParameterAnnotation(parameter,
+                desc,
+                visible));
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        checkEndMethod();
+        if (attr == null) {
+            throw new IllegalArgumentException("Invalid attribute (must not be null)");
+        }
+        super.visitAttribute(attr);
+    }
+
+    @Override
+    public void visitCode() {
+        startCode = true;
+        super.visitCode();
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        int mLocal;
+        int mStack;
+        switch (type) {
+            case Opcodes.F_NEW:
+            case Opcodes.F_FULL:
+                mLocal = Integer.MAX_VALUE;
+                mStack = Integer.MAX_VALUE;
+                break;
+
+            case Opcodes.F_SAME:
+                mLocal = 0;
+                mStack = 0;
+                break;
+
+            case Opcodes.F_SAME1:
+                mLocal = 0;
+                mStack = 1;
+                break;
+
+            case Opcodes.F_APPEND:
+            case Opcodes.F_CHOP:
+                mLocal = 3;
+                mStack = 0;
+                break;
+
+            default:
+                throw new IllegalArgumentException("Invalid frame type " + type);
+        }
+
+        if (nLocal > mLocal) {
+            throw new IllegalArgumentException("Invalid nLocal=" + nLocal
+                    + " for frame type " + type);
+        }
+        if (nStack > mStack) {
+            throw new IllegalArgumentException("Invalid nStack=" + nStack
+                    + " for frame type " + type);
+        }
+
+        if (type != Opcodes.F_CHOP) {
+            if (nLocal > 0 && (local == null || local.length < nLocal)) {
+                throw new IllegalArgumentException("Array local[] is shorter than nLocal");
+            }
+            for (int i = 0; i < nLocal; ++i) {
+                checkFrameValue(local[i]);
+            }
+        }
+        if (nStack > 0 && (stack == null || stack.length < nStack)) {
+            throw new IllegalArgumentException("Array stack[] is shorter than nStack");
+        }
+        for (int i = 0; i < nStack; ++i) {
+            checkFrameValue(stack[i]);
+        }
+
+        super.visitFrame(type, nLocal, local, nStack, stack);
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 0);
+        super.visitInsn(opcode);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 1);
+        switch (opcode) {
+            case Opcodes.BIPUSH:
+                checkSignedByte(operand, "Invalid operand");
+                break;
+            case Opcodes.SIPUSH:
+                checkSignedShort(operand, "Invalid operand");
+                break;
+            // case Constants.NEWARRAY:
+            default:
+                if (operand < Opcodes.T_BOOLEAN || operand > Opcodes.T_LONG) {
+                    throw new IllegalArgumentException("Invalid operand (must be an array type code T_...): "
+                            + operand);
+                }
+        }
+        super.visitIntInsn(opcode, operand);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 2);
+        checkUnsignedShort(var, "Invalid variable index");
+        super.visitVarInsn(opcode, var);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 3);
+        checkInternalName(type, "type");
+        if (opcode == Opcodes.NEW && type.charAt(0) == '[') {
+            throw new IllegalArgumentException("NEW cannot be used to create arrays: "
+                    + type);
+        }
+        super.visitTypeInsn(opcode, type);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 4);
+        checkInternalName(owner, "owner");
+        checkUnqualifiedName(version, name, "name");
+        checkDesc(desc, false);
+        super.visitFieldInsn(opcode, owner, name, desc);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 5);
+        checkMethodIdentifier(version, name, "name");
+        checkInternalName(owner, "owner");
+        checkMethodDesc(desc);
+        super.visitMethodInsn(opcode, owner, name, desc);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        checkStartCode();
+        checkEndCode();
+        checkMethodIdentifier(version, name, "name");
+        checkMethodDesc(desc);
+        if (bsm.getTag() != Opcodes.H_INVOKESTATIC
+                && bsm.getTag() != Opcodes.H_NEWINVOKESPECIAL)
+        {
+            throw new IllegalArgumentException("invalid handle tag "
+                    + bsm.getTag());
+        }
+        for (int i = 0; i < bsmArgs.length; i++) {
+            checkLDCConstant(bsmArgs[i]);
+        }
+        super.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        checkStartCode();
+        checkEndCode();
+        checkOpcode(opcode, 6);
+        checkLabel(label, false, "label");
+        checkNonDebugLabel(label);
+        super.visitJumpInsn(opcode, label);
+        usedLabels.add(label);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        checkStartCode();
+        checkEndCode();
+        checkLabel(label, false, "label");
+        if (labels.get(label) != null) {
+            throw new IllegalArgumentException("Already visited label");
+        }
+        labels.put(label, new Integer(insnCount));
+        super.visitLabel(label);
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        checkStartCode();
+        checkEndCode();
+        checkLDCConstant(cst);
+        super.visitLdcInsn(cst);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        checkStartCode();
+        checkEndCode();
+        checkUnsignedShort(var, "Invalid variable index");
+        checkSignedShort(increment, "Invalid increment");
+        super.visitIincInsn(var, increment);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        checkStartCode();
+        checkEndCode();
+        if (max < min) {
+            throw new IllegalArgumentException("Max = " + max
+                    + " must be greater than or equal to min = " + min);
+        }
+        checkLabel(dflt, false, "default label");
+        checkNonDebugLabel(dflt);
+        if (labels == null || labels.length != max - min + 1) {
+            throw new IllegalArgumentException("There must be max - min + 1 labels");
+        }
+        for (int i = 0; i < labels.length; ++i) {
+            checkLabel(labels[i], false, "label at index " + i);
+            checkNonDebugLabel(labels[i]);
+        }
+        super.visitTableSwitchInsn(min, max, dflt, labels);
+        for (int i = 0; i < labels.length; ++i) {
+            usedLabels.add(labels[i]);
+        }
+        ++insnCount;
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        checkEndCode();
+        checkStartCode();
+        checkLabel(dflt, false, "default label");
+        checkNonDebugLabel(dflt);
+        if (keys == null || labels == null || keys.length != labels.length) {
+            throw new IllegalArgumentException("There must be the same number of keys and labels");
+        }
+        for (int i = 0; i < labels.length; ++i) {
+            checkLabel(labels[i], false, "label at index " + i);
+            checkNonDebugLabel(labels[i]);
+        }
+        super.visitLookupSwitchInsn(dflt, keys, labels);
+        usedLabels.add(dflt);
+        for (int i = 0; i < labels.length; ++i) {
+            usedLabels.add(labels[i]);
+        }
+        ++insnCount;
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        checkStartCode();
+        checkEndCode();
+        checkDesc(desc, false);
+        if (desc.charAt(0) != '[') {
+            throw new IllegalArgumentException("Invalid descriptor (must be an array type descriptor): "
+                    + desc);
+        }
+        if (dims < 1) {
+            throw new IllegalArgumentException("Invalid dimensions (must be greater than 0): "
+                    + dims);
+        }
+        if (dims > desc.lastIndexOf('[') + 1) {
+            throw new IllegalArgumentException("Invalid dimensions (must not be greater than dims(desc)): "
+                    + dims);
+        }
+        super.visitMultiANewArrayInsn(desc, dims);
+        ++insnCount;
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type)
+    {
+        checkStartCode();
+        checkEndCode();
+        checkLabel(start, false, "start label");
+        checkLabel(end, false, "end label");
+        checkLabel(handler, false, "handler label");
+        checkNonDebugLabel(start);
+        checkNonDebugLabel(end);
+        checkNonDebugLabel(handler);
+        if (labels.get(start) != null || labels.get(end) != null
+                || labels.get(handler) != null)
+        {
+            throw new IllegalStateException("Try catch blocks must be visited before their labels");
+        }
+        if (type != null) {
+            checkInternalName(type, "type");
+        }
+        super.visitTryCatchBlock(start, end, handler, type);
+        handlers.add(start);
+        handlers.add(end);
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        checkStartCode();
+        checkEndCode();
+        checkUnqualifiedName(version, name, "name");
+        checkDesc(desc, false);
+        checkLabel(start, true, "start label");
+        checkLabel(end, true, "end label");
+        checkUnsignedShort(index, "Invalid variable index");
+        int s = labels.get(start).intValue();
+        int e = labels.get(end).intValue();
+        if (e < s) {
+            throw new IllegalArgumentException("Invalid start and end labels (end must be greater than start)");
+        }
+        super.visitLocalVariable(name, desc, signature, start, end, index);
+    }
+
+    @Override
+    public void visitLineNumber(final int line, final Label start) {
+        checkStartCode();
+        checkEndCode();
+        checkUnsignedShort(line, "Invalid line number");
+        checkLabel(start, true, "start label");
+        super.visitLineNumber(line, start);
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        checkStartCode();
+        checkEndCode();
+        endCode = true;
+        for (Label l : usedLabels) {
+            if (labels.get(l) == null) {
+                throw new IllegalStateException("Undefined label used");
+            }
+        }
+        for (int i = 0; i < handlers.size(); ) {
+            Integer start = labels.get(handlers.get(i++));
+            Integer end = labels.get(handlers.get(i++));
+            if (start == null || end == null) {
+                throw new IllegalStateException("Undefined try catch block labels");
+            }
+            if (end.intValue() <= start.intValue()) {
+                throw new IllegalStateException("Emty try catch block handler range");
+            }
+        }
+        checkUnsignedShort(maxStack, "Invalid max stack");
+        checkUnsignedShort(maxLocals, "Invalid max locals");
+        super.visitMaxs(maxStack, maxLocals);
+    }
+
+    @Override
+    public void visitEnd() {
+        checkEndMethod();
+        endMethod = true;
+        super.visitEnd();
+    }
+
+    // -------------------------------------------------------------------------
+
+    /**
+     * Checks that the visitCode method has been called.
+     */
+    void checkStartCode() {
+        if (!startCode) {
+            throw new IllegalStateException("Cannot visit instructions before visitCode has been called.");
+        }
+    }
+
+    /**
+     * Checks that the visitMaxs method has not been called.
+     */
+    void checkEndCode() {
+        if (endCode) {
+            throw new IllegalStateException("Cannot visit instructions after visitMaxs has been called.");
+        }
+    }
+
+    /**
+     * Checks that the visitEnd method has not been called.
+     */
+    void checkEndMethod() {
+        if (endMethod) {
+            throw new IllegalStateException("Cannot visit elements after visitEnd has been called.");
+        }
+    }
+
+    /**
+     * Checks a stack frame value.
+     *
+     * @param value the value to be checked.
+     */
+    void checkFrameValue(final Object value) {
+        if (value == Opcodes.TOP || value == Opcodes.INTEGER
+                || value == Opcodes.FLOAT || value == Opcodes.LONG
+                || value == Opcodes.DOUBLE || value == Opcodes.NULL
+                || value == Opcodes.UNINITIALIZED_THIS)
+        {
+            return;
+        }
+        if (value instanceof String) {
+            checkInternalName((String) value, "Invalid stack frame value");
+            return;
+        }
+        if (!(value instanceof Label)) {
+            throw new IllegalArgumentException("Invalid stack frame value: "
+                    + value);
+        } else {
+            usedLabels.add((Label) value);
+        }
+    }
+
+    /**
+     * Checks that the type of the given opcode is equal to the given type.
+     *
+     * @param opcode the opcode to be checked.
+     * @param type the expected opcode type.
+     */
+    static void checkOpcode(final int opcode, final int type) {
+        if (opcode < 0 || opcode > 199 || TYPE[opcode] != type) {
+            throw new IllegalArgumentException("Invalid opcode: " + opcode);
+        }
+    }
+
+    /**
+     * Checks that the given value is a signed byte.
+     *
+     * @param value the value to be checked.
+     * @param msg an message to be used in case of error.
+     */
+    static void checkSignedByte(final int value, final String msg) {
+        if (value < Byte.MIN_VALUE || value > Byte.MAX_VALUE) {
+            throw new IllegalArgumentException(msg
+                    + " (must be a signed byte): " + value);
+        }
+    }
+
+    /**
+     * Checks that the given value is a signed short.
+     *
+     * @param value the value to be checked.
+     * @param msg an message to be used in case of error.
+     */
+    static void checkSignedShort(final int value, final String msg) {
+        if (value < Short.MIN_VALUE || value > Short.MAX_VALUE) {
+            throw new IllegalArgumentException(msg
+                    + " (must be a signed short): " + value);
+        }
+    }
+
+    /**
+     * Checks that the given value is an unsigned short.
+     *
+     * @param value the value to be checked.
+     * @param msg an message to be used in case of error.
+     */
+    static void checkUnsignedShort(final int value, final String msg) {
+        if (value < 0 || value > 65535) {
+            throw new IllegalArgumentException(msg
+                    + " (must be an unsigned short): " + value);
+        }
+    }
+
+    /**
+     * Checks that the given value is an {@link Integer}, a{@link Float}, a
+     * {@link Long}, a {@link Double} or a {@link String}.
+     *
+     * @param cst the value to be checked.
+     */
+    static void checkConstant(final Object cst) {
+        if (!(cst instanceof Integer) && !(cst instanceof Float)
+                && !(cst instanceof Long) && !(cst instanceof Double)
+                && !(cst instanceof String))
+        {
+            throw new IllegalArgumentException("Invalid constant: " + cst);
+        }
+    }
+
+    void checkLDCConstant(final Object cst) {
+        if (cst instanceof Type) {
+            int s = ((Type) cst).getSort();
+            if (s != Type.OBJECT && s != Type.ARRAY && s != Type.METHOD) {
+                throw new IllegalArgumentException("Illegal LDC constant value");
+            }
+            if (s != Type.METHOD && (version & 0xFFFF) < Opcodes.V1_5) {
+                throw new IllegalArgumentException("ldc of a constant class requires at least version 1.5");
+            }
+            if (s == Type.METHOD && (version & 0xFFFF) < Opcodes.V1_7) {
+                throw new IllegalArgumentException("ldc of a method type requires at least version 1.7");
+            }
+        } else if (cst instanceof Handle) {
+            if ((version & 0xFFFF) < Opcodes.V1_7) {
+                throw new IllegalArgumentException("ldc of a handle requires at least version 1.7");
+            }
+            int tag = ((Handle) cst).getTag();
+            if (tag < Opcodes.H_GETFIELD || tag > Opcodes.H_INVOKEINTERFACE) {
+                throw new IllegalArgumentException("invalid handle tag "
+                        + tag);
+            }
+        } else {
+            checkConstant(cst);
+        }
+    }
+
+    /**
+     * Checks that the given string is a valid unqualified name.
+     *
+     * @param version the class version.
+     * @param name the string to be checked.
+     * @param msg a message to be used in case of error.
+     */
+    static void checkUnqualifiedName(
+        int version,
+        final String name,
+        final String msg)
+    {
+        if ((version & 0xFFFF) < Opcodes.V1_5) {
+            checkIdentifier(name, msg);
+        } else {
+            for (int i = 0; i < name.length(); ++i) {
+                if (".;[/".indexOf(name.charAt(i)) != -1) {
+                    throw new IllegalArgumentException("Invalid " + msg
+                            + " (must be a valid unqualified name): " + name);
+                }
+            }
+        }
+    }
+
+    /**
+     * Checks that the given string is a valid Java identifier.
+     *
+     * @param name the string to be checked.
+     * @param msg a message to be used in case of error.
+     */
+    static void checkIdentifier(final String name, final String msg) {
+        checkIdentifier(name, 0, -1, msg);
+    }
+
+    /**
+     * Checks that the given substring is a valid Java identifier.
+     *
+     * @param name the string to be checked.
+     * @param start index of the first character of the identifier (inclusive).
+     * @param end index of the last character of the identifier (exclusive). -1
+     *        is equivalent to <tt>name.length()</tt> if name is not
+     *        <tt>null</tt>.
+     * @param msg a message to be used in case of error.
+     */
+    static void checkIdentifier(
+        final String name,
+        final int start,
+        final int end,
+        final String msg)
+    {
+        if (name == null || (end == -1 ? name.length() <= start : end <= start))
+        {
+            throw new IllegalArgumentException("Invalid " + msg
+                    + " (must not be null or empty)");
+        }
+        if (!Character.isJavaIdentifierStart(name.charAt(start))) {
+            throw new IllegalArgumentException("Invalid " + msg
+                    + " (must be a valid Java identifier): " + name);
+        }
+        int max = end == -1 ? name.length() : end;
+        for (int i = start + 1; i < max; ++i) {
+            if (!Character.isJavaIdentifierPart(name.charAt(i))) {
+                throw new IllegalArgumentException("Invalid " + msg
+                        + " (must be a valid Java identifier): " + name);
+            }
+        }
+    }
+
+    /**
+     * Checks that the given string is a valid Java identifier or is equal to
+     * '&lt;init&gt;' or '&lt;clinit&gt;'.
+     *
+     * @param version the class version.
+     * @param name the string to be checked.
+     * @param msg a message to be used in case of error.
+     */
+    static void checkMethodIdentifier(
+        int version,
+        final String name,
+        final String msg)
+    {
+        if (name == null || name.length() == 0) {
+            throw new IllegalArgumentException("Invalid " + msg
+                    + " (must not be null or empty)");
+        }
+        if ("<init>".equals(name) || "<clinit>".equals(name)) {
+            return;
+        }
+        if ((version & 0xFFFF) >= Opcodes.V1_5) {
+            for (int i = 0; i < name.length(); ++i) {
+                if (".;[/<>".indexOf(name.charAt(i)) != -1) {
+                    throw new IllegalArgumentException("Invalid " + msg
+                            + " (must be a valid unqualified name): " + name);
+                }
+            }
+            return;
+        }
+        if (!Character.isJavaIdentifierStart(name.charAt(0))) {
+            throw new IllegalArgumentException("Invalid "
+                    + msg
+                    + " (must be a '<init>', '<clinit>' or a valid Java identifier): "
+                    + name);
+        }
+        for (int i = 1; i < name.length(); ++i) {
+            if (!Character.isJavaIdentifierPart(name.charAt(i))) {
+                throw new IllegalArgumentException("Invalid "
+                        + msg
+                        + " (must be '<init>' or '<clinit>' or a valid Java identifier): "
+                        + name);
+            }
+        }
+    }
+
+    /**
+     * Checks that the given string is a valid internal class name.
+     *
+     * @param name the string to be checked.
+     * @param msg a message to be used in case of error.
+     */
+    static void checkInternalName(final String name, final String msg) {
+        if (name == null || name.length() == 0) {
+            throw new IllegalArgumentException("Invalid " + msg
+                    + " (must not be null or empty)");
+        }
+        if (name.charAt(0) == '[') {
+            checkDesc(name, false);
+        } else {
+            checkInternalName(name, 0, -1, msg);
+        }
+    }
+
+    /**
+     * Checks that the given substring is a valid internal class name.
+     *
+     * @param name the string to be checked.
+     * @param start index of the first character of the identifier (inclusive).
+     * @param end index of the last character of the identifier (exclusive). -1
+     *        is equivalent to <tt>name.length()</tt> if name is not
+     *        <tt>null</tt>.
+     * @param msg a message to be used in case of error.
+     */
+    static void checkInternalName(
+        final String name,
+        final int start,
+        final int end,
+        final String msg)
+    {
+        int max = end == -1 ? name.length() : end;
+        try {
+            int begin = start;
+            int slash;
+            do {
+                slash = name.indexOf('/', begin + 1);
+                if (slash == -1 || slash > max) {
+                    slash = max;
+                }
+                checkIdentifier(name, begin, slash, null);
+                begin = slash + 1;
+            } while (slash != max);
+        } catch (IllegalArgumentException _) {
+            throw new IllegalArgumentException("Invalid "
+                    + msg
+                    + " (must be a fully qualified class name in internal form): "
+                    + name);
+        }
+    }
+
+    /**
+     * Checks that the given string is a valid type descriptor.
+     *
+     * @param desc the string to be checked.
+     * @param canBeVoid <tt>true</tt> if <tt>V</tt> can be considered valid.
+     */
+    static void checkDesc(final String desc, final boolean canBeVoid) {
+        int end = checkDesc(desc, 0, canBeVoid);
+        if (end != desc.length()) {
+            throw new IllegalArgumentException("Invalid descriptor: " + desc);
+        }
+    }
+
+    /**
+     * Checks that a the given substring is a valid type descriptor.
+     *
+     * @param desc the string to be checked.
+     * @param start index of the first character of the identifier (inclusive).
+     * @param canBeVoid <tt>true</tt> if <tt>V</tt> can be considered valid.
+     * @return the index of the last character of the type decriptor, plus one.
+     */
+    static int checkDesc(
+        final String desc,
+        final int start,
+        final boolean canBeVoid)
+    {
+        if (desc == null || start >= desc.length()) {
+            throw new IllegalArgumentException("Invalid type descriptor (must not be null or empty)");
+        }
+        int index;
+        switch (desc.charAt(start)) {
+            case 'V':
+                if (canBeVoid) {
+                    return start + 1;
+                } else {
+                    throw new IllegalArgumentException("Invalid descriptor: "
+                            + desc);
+                }
+            case 'Z':
+            case 'C':
+            case 'B':
+            case 'S':
+            case 'I':
+            case 'F':
+            case 'J':
+            case 'D':
+                return start + 1;
+            case '[':
+                index = start + 1;
+                while (index < desc.length() && desc.charAt(index) == '[') {
+                    ++index;
+                }
+                if (index < desc.length()) {
+                    return checkDesc(desc, index, false);
+                } else {
+                    throw new IllegalArgumentException("Invalid descriptor: "
+                            + desc);
+                }
+            case 'L':
+                index = desc.indexOf(';', start);
+                if (index == -1 || index - start < 2) {
+                    throw new IllegalArgumentException("Invalid descriptor: "
+                            + desc);
+                }
+                try {
+                    checkInternalName(desc, start + 1, index, null);
+                } catch (IllegalArgumentException _) {
+                    throw new IllegalArgumentException("Invalid descriptor: "
+                            + desc);
+                }
+                return index + 1;
+            default:
+                throw new IllegalArgumentException("Invalid descriptor: "
+                        + desc);
+        }
+    }
+
+    /**
+     * Checks that the given string is a valid method descriptor.
+     *
+     * @param desc the string to be checked.
+     */
+    static void checkMethodDesc(final String desc) {
+        if (desc == null || desc.length() == 0) {
+            throw new IllegalArgumentException("Invalid method descriptor (must not be null or empty)");
+        }
+        if (desc.charAt(0) != '(' || desc.length() < 3) {
+            throw new IllegalArgumentException("Invalid descriptor: " + desc);
+        }
+        int start = 1;
+        if (desc.charAt(start) != ')') {
+            do {
+                if (desc.charAt(start) == 'V') {
+                    throw new IllegalArgumentException("Invalid descriptor: "
+                            + desc);
+                }
+                start = checkDesc(desc, start, false);
+            } while (start < desc.length() && desc.charAt(start) != ')');
+        }
+        start = checkDesc(desc, start + 1, true);
+        if (start != desc.length()) {
+            throw new IllegalArgumentException("Invalid descriptor: " + desc);
+        }
+    }
+
+    /**
+     * Checks a class signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     */
+    static void checkClassSignature(final String signature) {
+        // ClassSignature:
+        // FormalTypeParameters? ClassTypeSignature ClassTypeSignature*
+
+        int pos = 0;
+        if (getChar(signature, 0) == '<') {
+            pos = checkFormalTypeParameters(signature, pos);
+        }
+        pos = checkClassTypeSignature(signature, pos);
+        while (getChar(signature, pos) == 'L') {
+            pos = checkClassTypeSignature(signature, pos);
+        }
+        if (pos != signature.length()) {
+            throw new IllegalArgumentException(signature + ": error at index "
+                    + pos);
+        }
+    }
+
+    /**
+     * Checks a method signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     */
+    static void checkMethodSignature(final String signature) {
+        // MethodTypeSignature:
+        // FormalTypeParameters? ( TypeSignature* ) ( TypeSignature | V ) (
+        // ^ClassTypeSignature | ^TypeVariableSignature )*
+
+        int pos = 0;
+        if (getChar(signature, 0) == '<') {
+            pos = checkFormalTypeParameters(signature, pos);
+        }
+        pos = checkChar('(', signature, pos);
+        while ("ZCBSIFJDL[T".indexOf(getChar(signature, pos)) != -1) {
+            pos = checkTypeSignature(signature, pos);
+        }
+        pos = checkChar(')', signature, pos);
+        if (getChar(signature, pos) == 'V') {
+            ++pos;
+        } else {
+            pos = checkTypeSignature(signature, pos);
+        }
+        while (getChar(signature, pos) == '^') {
+            ++pos;
+            if (getChar(signature, pos) == 'L') {
+                pos = checkClassTypeSignature(signature, pos);
+            } else {
+                pos = checkTypeVariableSignature(signature, pos);
+            }
+        }
+        if (pos != signature.length()) {
+            throw new IllegalArgumentException(signature + ": error at index "
+                    + pos);
+        }
+    }
+
+    /**
+     * Checks a field signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     */
+    static void checkFieldSignature(final String signature) {
+        int pos = checkFieldTypeSignature(signature, 0);
+        if (pos != signature.length()) {
+            throw new IllegalArgumentException(signature + ": error at index "
+                    + pos);
+        }
+    }
+
+    /**
+     * Checks the formal type parameters of a class or method signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkFormalTypeParameters(final String signature, int pos)
+    {
+        // FormalTypeParameters:
+        // < FormalTypeParameter+ >
+
+        pos = checkChar('<', signature, pos);
+        pos = checkFormalTypeParameter(signature, pos);
+        while (getChar(signature, pos) != '>') {
+            pos = checkFormalTypeParameter(signature, pos);
+        }
+        return pos + 1;
+    }
+
+    /**
+     * Checks a formal type parameter of a class or method signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkFormalTypeParameter(final String signature, int pos)
+    {
+        // FormalTypeParameter:
+        // Identifier : FieldTypeSignature? (: FieldTypeSignature)*
+
+        pos = checkIdentifier(signature, pos);
+        pos = checkChar(':', signature, pos);
+        if ("L[T".indexOf(getChar(signature, pos)) != -1) {
+            pos = checkFieldTypeSignature(signature, pos);
+        }
+        while (getChar(signature, pos) == ':') {
+            pos = checkFieldTypeSignature(signature, pos + 1);
+        }
+        return pos;
+    }
+
+    /**
+     * Checks a field type signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkFieldTypeSignature(final String signature, int pos)
+    {
+        // FieldTypeSignature:
+        // ClassTypeSignature | ArrayTypeSignature | TypeVariableSignature
+        //
+        // ArrayTypeSignature:
+        // [ TypeSignature
+
+        switch (getChar(signature, pos)) {
+            case 'L':
+                return checkClassTypeSignature(signature, pos);
+            case '[':
+                return checkTypeSignature(signature, pos + 1);
+            default:
+                return checkTypeVariableSignature(signature, pos);
+        }
+    }
+
+    /**
+     * Checks a class type signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkClassTypeSignature(final String signature, int pos)
+    {
+        // ClassTypeSignature:
+        // L Identifier ( / Identifier )* TypeArguments? ( . Identifier
+        // TypeArguments? )* ;
+
+        pos = checkChar('L', signature, pos);
+        pos = checkIdentifier(signature, pos);
+        while (getChar(signature, pos) == '/') {
+            pos = checkIdentifier(signature, pos + 1);
+        }
+        if (getChar(signature, pos) == '<') {
+            pos = checkTypeArguments(signature, pos);
+        }
+        while (getChar(signature, pos) == '.') {
+            pos = checkIdentifier(signature, pos + 1);
+            if (getChar(signature, pos) == '<') {
+                pos = checkTypeArguments(signature, pos);
+            }
+        }
+        return checkChar(';', signature, pos);
+    }
+
+    /**
+     * Checks the type arguments in a class type signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkTypeArguments(final String signature, int pos) {
+        // TypeArguments:
+        // < TypeArgument+ >
+
+        pos = checkChar('<', signature, pos);
+        pos = checkTypeArgument(signature, pos);
+        while (getChar(signature, pos) != '>') {
+            pos = checkTypeArgument(signature, pos);
+        }
+        return pos + 1;
+    }
+
+    /**
+     * Checks a type argument in a class type signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkTypeArgument(final String signature, int pos) {
+        // TypeArgument:
+        // * | ( ( + | - )? FieldTypeSignature )
+
+        char c = getChar(signature, pos);
+        if (c == '*') {
+            return pos + 1;
+        } else if (c == '+' || c == '-') {
+            pos++;
+        }
+        return checkFieldTypeSignature(signature, pos);
+    }
+
+    /**
+     * Checks a type variable signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkTypeVariableSignature(
+        final String signature,
+        int pos)
+    {
+        // TypeVariableSignature:
+        // T Identifier ;
+
+        pos = checkChar('T', signature, pos);
+        pos = checkIdentifier(signature, pos);
+        return checkChar(';', signature, pos);
+    }
+
+    /**
+     * Checks a type signature.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkTypeSignature(final String signature, int pos) {
+        // TypeSignature:
+        // Z | C | B | S | I | F | J | D | FieldTypeSignature
+
+        switch (getChar(signature, pos)) {
+            case 'Z':
+            case 'C':
+            case 'B':
+            case 'S':
+            case 'I':
+            case 'F':
+            case 'J':
+            case 'D':
+                return pos + 1;
+            default:
+                return checkFieldTypeSignature(signature, pos);
+        }
+    }
+
+    /**
+     * Checks an identifier.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkIdentifier(final String signature, int pos) {
+        if (!Character.isJavaIdentifierStart(getChar(signature, pos))) {
+            throw new IllegalArgumentException(signature
+                    + ": identifier expected at index " + pos);
+        }
+        ++pos;
+        while (Character.isJavaIdentifierPart(getChar(signature, pos))) {
+            ++pos;
+        }
+        return pos;
+    }
+
+    /**
+     * Checks a single character.
+     *
+     * @param signature a string containing the signature that must be checked.
+     * @param pos index of first character to be checked.
+     * @return the index of the first character after the checked part.
+     */
+    private static int checkChar(final char c, final String signature, int pos)
+    {
+        if (getChar(signature, pos) == c) {
+            return pos + 1;
+        }
+        throw new IllegalArgumentException(signature + ": '" + c
+                + "' expected at index " + pos);
+    }
+
+    /**
+     * Returns the signature car at the given index.
+     *
+     * @param signature a signature.
+     * @param pos an index in signature.
+     * @return the character at the given index, or 0 if there is no such
+     *         character.
+     */
+    private static char getChar(final String signature, int pos) {
+        return pos < signature.length() ? signature.charAt(pos) : (char) 0;
+    }
+
+    /**
+     * Checks that the given label is not null. This method can also check that
+     * the label has been visited.
+     *
+     * @param label the label to be checked.
+     * @param checkVisited <tt>true</tt> to check that the label has been
+     *        visited.
+     * @param msg a message to be used in case of error.
+     */
+    void checkLabel(
+        final Label label,
+        final boolean checkVisited,
+        final String msg)
+    {
+        if (label == null) {
+            throw new IllegalArgumentException("Invalid " + msg
+                    + " (must not be null)");
+        }
+        if (checkVisited && labels.get(label) == null) {
+            throw new IllegalArgumentException("Invalid " + msg
+                    + " (must be visited first)");
+        }
+    }
+
+    /**
+     * Checks that the given label is not a label used only for debug purposes.
+     *
+     * @param label the label to be checked.
+     */
+    private static void checkNonDebugLabel(final Label label) {
+        Field f = getLabelStatusField();
+        int status = 0;
+        try {
+            status = f == null ? 0 : ((Integer) f.get(label)).intValue();
+        } catch (IllegalAccessException e) {
+            throw new Error("Internal error");
+        }
+        if ((status & 0x01) != 0) {
+            throw new IllegalArgumentException("Labels used for debug info cannot be reused for control flow");
+        }
+    }
+
+    /**
+     * Returns the Field object corresponding to the Label.status field.
+     *
+     * @return the Field object corresponding to the Label.status field.
+     */
+    private static Field getLabelStatusField() {
+        if (labelStatusField == null) {
+            labelStatusField = getLabelField("a");
+            if (labelStatusField == null) {
+                labelStatusField = getLabelField("status");
+            }
+        }
+        return labelStatusField;
+    }
+
+    /**
+     * Returns the field of the Label class whose name is given.
+     *
+     * @param name a field name.
+     * @return the field of the Label class whose name is given, or null.
+     */
+    private static Field getLabelField(final String name) {
+        try {
+            Field f = Label.class.getDeclaredField(name);
+            f.setAccessible(true);
+            return f;
+        } catch (NoSuchFieldException e) {
+            return null;
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/CheckSignatureAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,358 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.signature.SignatureVisitor;
+
+/**
+ * A {@link SignatureVisitor} that checks that its methods are properly used.
+ *
+ * @author Eric Bruneton
+ */
+public class CheckSignatureAdapter extends SignatureVisitor {
+
+    /**
+     * Type to be used to check class signatures. See
+     * {@link #CheckSignatureAdapter(int, SignatureVisitor) CheckSignatureAdapter}.
+     */
+    public static final int CLASS_SIGNATURE = 0;
+
+    /**
+     * Type to be used to check method signatures. See
+     * {@link #CheckSignatureAdapter(int, SignatureVisitor) CheckSignatureAdapter}.
+     */
+    public static final int METHOD_SIGNATURE = 1;
+
+    /**
+     * Type to be used to check type signatures.See
+     * {@link #CheckSignatureAdapter(int, SignatureVisitor) CheckSignatureAdapter}.
+     */
+    public static final int TYPE_SIGNATURE = 2;
+
+    private static final int EMPTY = 1;
+
+    private static final int FORMAL = 2;
+
+    private static final int BOUND = 4;
+
+    private static final int SUPER = 8;
+
+    private static final int PARAM = 16;
+
+    private static final int RETURN = 32;
+
+    private static final int SIMPLE_TYPE = 64;
+
+    private static final int CLASS_TYPE = 128;
+
+    private static final int END = 256;
+
+    /**
+     * Type of the signature to be checked.
+     */
+    private final int type;
+
+    /**
+     * State of the automaton used to check the order of method calls.
+     */
+    private int state;
+
+    /**
+     * <tt>true</tt> if the checked type signature can be 'V'.
+     */
+    private boolean canBeVoid;
+
+    /**
+     * The visitor to which this adapter must delegate calls. May be
+     * <tt>null</tt>.
+     */
+    private final SignatureVisitor sv;
+
+    /**
+     * Creates a new {@link CheckSignatureAdapter} object. <i>Subclasses must
+     * not use this constructor</i>. Instead, they must use the
+     * {@link #CheckSignatureAdapter(int, int, SignatureVisitor)} version.
+     *
+     * @param type the type of signature to be checked. See
+     *        {@link #CLASS_SIGNATURE}, {@link #METHOD_SIGNATURE} and
+     *        {@link #TYPE_SIGNATURE}.
+     * @param sv the visitor to which this adapter must delegate calls. May be
+     *        <tt>null</tt>.
+     */
+    public CheckSignatureAdapter(final int type, final SignatureVisitor sv) {
+        this(Opcodes.ASM4, type, sv);
+    }
+
+    /**
+     * Creates a new {@link CheckSignatureAdapter} object.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     * @param type the type of signature to be checked. See
+     *        {@link #CLASS_SIGNATURE}, {@link #METHOD_SIGNATURE} and
+     *        {@link #TYPE_SIGNATURE}.
+     * @param sv the visitor to which this adapter must delegate calls. May be
+     *        <tt>null</tt>.
+     */
+    protected CheckSignatureAdapter(
+        final int api,
+        final int type,
+        final SignatureVisitor sv)
+    {
+        super(api);
+        this.type = type;
+        this.state = EMPTY;
+        this.sv = sv;
+    }
+
+    // class and method signatures
+
+    @Override
+    public void visitFormalTypeParameter(final String name) {
+        if (type == TYPE_SIGNATURE
+                || (state != EMPTY && state != FORMAL && state != BOUND))
+        {
+            throw new IllegalStateException();
+        }
+        CheckMethodAdapter.checkIdentifier(name, "formal type parameter");
+        state = FORMAL;
+        if (sv != null) {
+            sv.visitFormalTypeParameter(name);
+        }
+    }
+
+    @Override
+    public SignatureVisitor visitClassBound() {
+        if (state != FORMAL) {
+            throw new IllegalStateException();
+        }
+        state = BOUND;
+        SignatureVisitor v = sv == null ? null : sv.visitClassBound();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    @Override
+    public SignatureVisitor visitInterfaceBound() {
+        if (state != FORMAL && state != BOUND) {
+            throw new IllegalArgumentException();
+        }
+        SignatureVisitor v = sv == null ? null : sv.visitInterfaceBound();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    // class signatures
+
+    @Override
+    public SignatureVisitor visitSuperclass() {
+        if (type != CLASS_SIGNATURE || (state & (EMPTY | FORMAL | BOUND)) == 0)
+        {
+            throw new IllegalArgumentException();
+        }
+        state = SUPER;
+        SignatureVisitor v = sv == null ? null : sv.visitSuperclass();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    @Override
+    public SignatureVisitor visitInterface() {
+        if (state != SUPER) {
+            throw new IllegalStateException();
+        }
+        SignatureVisitor v = sv == null ? null : sv.visitInterface();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    // method signatures
+
+    @Override
+    public SignatureVisitor visitParameterType() {
+        if (type != METHOD_SIGNATURE
+                || (state & (EMPTY | FORMAL | BOUND | PARAM)) == 0)
+        {
+            throw new IllegalArgumentException();
+        }
+        state = PARAM;
+        SignatureVisitor v = sv == null ? null : sv.visitParameterType();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    @Override
+    public SignatureVisitor visitReturnType() {
+        if (type != METHOD_SIGNATURE
+                || (state & (EMPTY | FORMAL | BOUND | PARAM)) == 0)
+        {
+            throw new IllegalArgumentException();
+        }
+        state = RETURN;
+        SignatureVisitor v = sv == null ? null : sv.visitReturnType();
+        CheckSignatureAdapter cv = new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+        cv.canBeVoid = true;
+        return cv;
+    }
+
+    @Override
+    public SignatureVisitor visitExceptionType() {
+        if (state != RETURN) {
+            throw new IllegalStateException();
+        }
+        SignatureVisitor v = sv == null ? null : sv.visitExceptionType();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    // type signatures
+
+    @Override
+    public void visitBaseType(final char descriptor) {
+        if (type != TYPE_SIGNATURE || state != EMPTY) {
+            throw new IllegalStateException();
+        }
+        if (descriptor == 'V') {
+            if (!canBeVoid) {
+                throw new IllegalArgumentException();
+            }
+        } else {
+            if ("ZCBSIFJD".indexOf(descriptor) == -1) {
+                throw new IllegalArgumentException();
+            }
+        }
+        state = SIMPLE_TYPE;
+        if (sv != null) {
+            sv.visitBaseType(descriptor);
+        }
+    }
+
+    @Override
+    public void visitTypeVariable(final String name) {
+        if (type != TYPE_SIGNATURE || state != EMPTY) {
+            throw new IllegalStateException();
+        }
+        CheckMethodAdapter.checkIdentifier(name, "type variable");
+        state = SIMPLE_TYPE;
+        if (sv != null) {
+            sv.visitTypeVariable(name);
+        }
+    }
+
+    @Override
+    public SignatureVisitor visitArrayType() {
+        if (type != TYPE_SIGNATURE || state != EMPTY) {
+            throw new IllegalStateException();
+        }
+        state = SIMPLE_TYPE;
+        SignatureVisitor v = sv == null ? null : sv.visitArrayType();
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    @Override
+    public void visitClassType(final String name) {
+        if (type != TYPE_SIGNATURE || state != EMPTY) {
+            throw new IllegalStateException();
+        }
+        CheckMethodAdapter.checkInternalName(name, "class name");
+        state = CLASS_TYPE;
+        if (sv != null) {
+            sv.visitClassType(name);
+        }
+    }
+
+    @Override
+    public void visitInnerClassType(final String name) {
+        if (state != CLASS_TYPE) {
+            throw new IllegalStateException();
+        }
+        CheckMethodAdapter.checkIdentifier(name, "inner class name");
+        if (sv != null) {
+            sv.visitInnerClassType(name);
+        }
+    }
+
+    @Override
+    public void visitTypeArgument() {
+        if (state != CLASS_TYPE) {
+            throw new IllegalStateException();
+        }
+        if (sv != null) {
+            sv.visitTypeArgument();
+        }
+    }
+
+    @Override
+    public SignatureVisitor visitTypeArgument(final char wildcard) {
+        if (state != CLASS_TYPE) {
+            throw new IllegalStateException();
+        }
+        if ("+-=".indexOf(wildcard) == -1) {
+            throw new IllegalArgumentException();
+        }
+        SignatureVisitor v = sv == null ? null : sv.visitTypeArgument(wildcard);
+        return new CheckSignatureAdapter(TYPE_SIGNATURE, v);
+    }
+
+    @Override
+    public void visitEnd() {
+        if (state != CLASS_TYPE) {
+            throw new IllegalStateException();
+        }
+        state = END;
+        if (sv != null) {
+            sv.visitEnd();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/Printer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,587 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.io.PrintWriter;
+import java.util.ArrayList;
+import java.util.List;
+
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * An abstract converter from visit events to text.
+ *
+ * @author Eric Bruneton
+ */
+public abstract class Printer {
+
+    /**
+     * The names of the Java Virtual Machine opcodes.
+     */
+    public static final String[] OPCODES;
+
+    /**
+     * The names of the for <code>operand</code> parameter values of the
+     * {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitIntInsn} method when
+     * <code>opcode</code> is <code>NEWARRAY</code>.
+     */
+    public static final String[] TYPES;
+
+    /**
+     * The names of the <code>tag</code> field values for
+     * {@link jdk.internal.org.objectweb.asm.Handle}.
+     */
+    public static final String[] HANDLE_TAG;
+
+    static {
+        String s = "NOP,ACONST_NULL,ICONST_M1,ICONST_0,ICONST_1,ICONST_2,"
+                + "ICONST_3,ICONST_4,ICONST_5,LCONST_0,LCONST_1,FCONST_0,"
+                + "FCONST_1,FCONST_2,DCONST_0,DCONST_1,BIPUSH,SIPUSH,LDC,,,"
+                + "ILOAD,LLOAD,FLOAD,DLOAD,ALOAD,,,,,,,,,,,,,,,,,,,,,IALOAD,"
+                + "LALOAD,FALOAD,DALOAD,AALOAD,BALOAD,CALOAD,SALOAD,ISTORE,"
+                + "LSTORE,FSTORE,DSTORE,ASTORE,,,,,,,,,,,,,,,,,,,,,IASTORE,"
+                + "LASTORE,FASTORE,DASTORE,AASTORE,BASTORE,CASTORE,SASTORE,POP,"
+                + "POP2,DUP,DUP_X1,DUP_X2,DUP2,DUP2_X1,DUP2_X2,SWAP,IADD,LADD,"
+                + "FADD,DADD,ISUB,LSUB,FSUB,DSUB,IMUL,LMUL,FMUL,DMUL,IDIV,LDIV,"
+                + "FDIV,DDIV,IREM,LREM,FREM,DREM,INEG,LNEG,FNEG,DNEG,ISHL,LSHL,"
+                + "ISHR,LSHR,IUSHR,LUSHR,IAND,LAND,IOR,LOR,IXOR,LXOR,IINC,I2L,"
+                + "I2F,I2D,L2I,L2F,L2D,F2I,F2L,F2D,D2I,D2L,D2F,I2B,I2C,I2S,LCMP,"
+                + "FCMPL,FCMPG,DCMPL,DCMPG,IFEQ,IFNE,IFLT,IFGE,IFGT,IFLE,"
+                + "IF_ICMPEQ,IF_ICMPNE,IF_ICMPLT,IF_ICMPGE,IF_ICMPGT,IF_ICMPLE,"
+                + "IF_ACMPEQ,IF_ACMPNE,GOTO,JSR,RET,TABLESWITCH,LOOKUPSWITCH,"
+                + "IRETURN,LRETURN,FRETURN,DRETURN,ARETURN,RETURN,GETSTATIC,"
+                + "PUTSTATIC,GETFIELD,PUTFIELD,INVOKEVIRTUAL,INVOKESPECIAL,"
+                + "INVOKESTATIC,INVOKEINTERFACE,INVOKEDYNAMIC,NEW,NEWARRAY,"
+                + "ANEWARRAY,ARRAYLENGTH,ATHROW,CHECKCAST,INSTANCEOF,"
+                + "MONITORENTER,MONITOREXIT,,MULTIANEWARRAY,IFNULL,IFNONNULL,";
+        OPCODES = new String[200];
+        int i = 0;
+        int j = 0;
+        int l;
+        while ((l = s.indexOf(',', j)) > 0) {
+            OPCODES[i++] = j + 1 == l ? null : s.substring(j, l);
+            j = l + 1;
+        }
+
+        s = "T_BOOLEAN,T_CHAR,T_FLOAT,T_DOUBLE,T_BYTE,T_SHORT,T_INT,T_LONG,";
+        TYPES = new String[12];
+        j = 0;
+        i = 4;
+        while ((l = s.indexOf(',', j)) > 0) {
+            TYPES[i++] = s.substring(j, l);
+            j = l + 1;
+        }
+
+        s = "H_GETFIELD,H_GETSTATIC,H_PUTFIELD,H_PUTSTATIC,"
+          + "H_INVOKEVIRTUAL,H_INVOKESTATIC,H_INVOKESPECIAL,"
+          + "H_NEWINVOKESPECIAL,H_INVOKEINTERFACE,";
+        HANDLE_TAG = new String[10];
+        j = 0;
+        i = 1;
+        while ((l = s.indexOf(',', j)) > 0) {
+            HANDLE_TAG[i++] = s.substring(j, l);
+            j = l + 1;
+        }
+    }
+
+    /**
+     * The ASM API version implemented by this class. The value of this field
+     * must be one of {@link Opcodes#ASM4}.
+     */
+    protected final int api;
+
+    /**
+     * A buffer that can be used to create strings.
+     */
+    protected final StringBuffer buf;
+
+    /**
+     * The text to be printed. Since the code of methods is not necessarily
+     * visited in sequential order, one method after the other, but can be
+     * interlaced (some instructions from method one, then some instructions
+     * from method two, then some instructions from method one again...), it is
+     * not possible to print the visited instructions directly to a sequential
+     * stream. A class is therefore printed in a two steps process: a string
+     * tree is constructed during the visit, and printed to a sequential stream
+     * at the end of the visit. This string tree is stored in this field, as a
+     * string list that can contain other string lists, which can themselves
+     * contain other string lists, and so on.
+     */
+    public final List<Object> text;
+
+    /**
+     * Constructs a new {@link Printer}.
+     */
+    protected Printer(final int api) {
+        this.api = api;
+        this.buf = new StringBuffer();
+        this.text = new ArrayList<Object>();
+    }
+
+    /**
+     * Class header.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visit}.
+     */
+    public abstract void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces);
+
+    /**
+     * Class source.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitSource}.
+     */
+    public abstract void visitSource(final String file, final String debug);
+
+    /**
+     * Class outer class.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitOuterClass}.
+     */
+    public abstract void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc);
+
+    /**
+     * Class annotation.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitAnnotation}.
+     */
+    public abstract Printer visitClassAnnotation(
+        final String desc,
+        final boolean visible);
+
+    /**
+     * Class attribute.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitAttribute}.
+     */
+    public abstract void visitClassAttribute(final Attribute attr);
+
+    /**
+     * Class inner name.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitInnerClass}.
+     */
+    public abstract void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access);
+
+    /**
+     * Class field.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitField}.
+     */
+    public abstract Printer visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value);
+
+    /**
+     * Class method.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitMethod}.
+     */
+    public abstract Printer visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions);
+
+    /**
+     * Class end.
+     * See {@link jdk.internal.org.objectweb.asm.ClassVisitor#visitEnd}.
+     */
+    public abstract void visitClassEnd();
+
+    // ------------------------------------------------------------------------
+    // Annotations
+    // ------------------------------------------------------------------------
+
+    /**
+     * Annotation value.
+     * See {@link jdk.internal.org.objectweb.asm.AnnotationVisitor#visit}.
+     */
+    public abstract void visit(final String name, final Object value);
+
+    /**
+     * Annotation enum value.
+     * See {@link jdk.internal.org.objectweb.asm.AnnotationVisitor#visitEnum}.
+     */
+    public abstract void visitEnum(
+        final String name,
+        final String desc,
+        final String value);
+
+    /**
+     * Nested annotation value.
+     * See {@link jdk.internal.org.objectweb.asm.AnnotationVisitor#visitAnnotation}.
+     */
+    public abstract Printer visitAnnotation(
+        final String name,
+        final String desc);
+
+    /**
+     * Annotation array value.
+     * See {@link jdk.internal.org.objectweb.asm.AnnotationVisitor#visitArray}.
+     */
+    public abstract Printer visitArray(final String name);
+
+    /**
+     * Annotation end.
+     * See {@link jdk.internal.org.objectweb.asm.AnnotationVisitor#visitEnd}.
+     */
+    public abstract void visitAnnotationEnd();
+
+    // ------------------------------------------------------------------------
+    // Fields
+    // ------------------------------------------------------------------------
+
+    /**
+     * Field annotation.
+     * See {@link jdk.internal.org.objectweb.asm.FieldVisitor#visitAnnotation}.
+     */
+    public abstract Printer visitFieldAnnotation(
+        final String desc,
+        final boolean visible);
+
+    /**
+     * Field attribute.
+     * See {@link jdk.internal.org.objectweb.asm.FieldVisitor#visitAttribute}.
+     */
+    public abstract void visitFieldAttribute(final Attribute attr);
+
+    /**
+     * Field end.
+     * See {@link jdk.internal.org.objectweb.asm.FieldVisitor#visitEnd}.
+     */
+    public abstract void visitFieldEnd();
+
+    // ------------------------------------------------------------------------
+    // Methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Method default annotation.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitAnnotationDefault}.
+     */
+    public abstract Printer visitAnnotationDefault();
+
+    /**
+     * Method annotation.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitAnnotation}.
+     */
+    public abstract Printer visitMethodAnnotation(
+        final String desc,
+        final boolean visible);
+
+    /**
+     * Method parameter annotation.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitParameterAnnotation}.
+     */
+    public abstract Printer visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible);
+
+    /**
+     * Method attribute.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitAttribute}.
+     */
+    public abstract void visitMethodAttribute(final Attribute attr);
+
+    /**
+     * Method start.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitCode}.
+     */
+    public abstract void visitCode();
+
+    /**
+     * Method stack frame.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitFrame}.
+     */
+    public abstract void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitInsn}.
+     */
+    public abstract void visitInsn(final int opcode);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitIntInsn}.
+     */
+    public abstract void visitIntInsn(final int opcode, final int operand);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitVarInsn}.
+     */
+    public abstract void visitVarInsn(final int opcode, final int var);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitTypeInsn}.
+     */
+    public abstract void visitTypeInsn(final int opcode, final String type);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitFieldInsn}.
+     */
+    public abstract void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitMethodInsn}.
+     */
+    public abstract void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitInvokeDynamicInsn}.
+     */
+    public abstract void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitJumpInsn}.
+     */
+    public abstract void visitJumpInsn(final int opcode, final Label label);
+
+    /**
+     * Method label.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitLabel}.
+     */
+    public abstract void visitLabel(final Label label);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitLdcInsn}.
+     */
+    public abstract void visitLdcInsn(final Object cst);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitIincInsn}.
+     */
+    public abstract void visitIincInsn(final int var, final int increment);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitTableSwitchInsn}.
+     */
+    public abstract void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitLookupSwitchInsn}.
+     */
+    public abstract void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels);
+
+    /**
+     * Method instruction.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitMultiANewArrayInsn}.
+     */
+    public abstract void visitMultiANewArrayInsn(
+        final String desc,
+        final int dims);
+
+    /**
+     * Method exception handler.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitTryCatchBlock}.
+     */
+    public abstract void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type);
+
+    /**
+     * Method debug info.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitLocalVariable}.
+     */
+    public abstract void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index);
+
+    /**
+     * Method debug info.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitLineNumber}.
+     */
+    public abstract void visitLineNumber(final int line, final Label start);
+
+    /**
+     * Method max stack and max locals.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitMaxs}.
+     */
+    public abstract void visitMaxs(final int maxStack, final int maxLocals);
+
+    /**
+     * Method end.
+     * See {@link jdk.internal.org.objectweb.asm.MethodVisitor#visitEnd}.
+     */
+    public abstract void visitMethodEnd();
+
+    /**
+     * Returns the text constructed by this visitor.
+     *
+     * @return the text constructed by this visitor.
+     */
+    public List<Object> getText() {
+        return text;
+    }
+
+    /**
+     * Prints the text constructed by this visitor.
+     *
+     * @param pw the print writer to be used.
+     */
+    public void print(final PrintWriter pw) {
+        printList(pw, text);
+    }
+
+    /**
+     * Appends a quoted string to a given buffer.
+     *
+     * @param buf the buffer where the string must be added.
+     * @param s the string to be added.
+     */
+    public static void appendString(final StringBuffer buf, final String s) {
+        buf.append('\"');
+        for (int i = 0; i < s.length(); ++i) {
+            char c = s.charAt(i);
+            if (c == '\n') {
+                buf.append("\\n");
+            } else if (c == '\r') {
+                buf.append("\\r");
+            } else if (c == '\\') {
+                buf.append("\\\\");
+            } else if (c == '"') {
+                buf.append("\\\"");
+            } else if (c < 0x20 || c > 0x7f) {
+                buf.append("\\u");
+                if (c < 0x10) {
+                    buf.append("000");
+                } else if (c < 0x100) {
+                    buf.append("00");
+                } else if (c < 0x1000) {
+                    buf.append('0');
+                }
+                buf.append(Integer.toString(c, 16));
+            } else {
+                buf.append(c);
+            }
+        }
+        buf.append('\"');
+    }
+
+    /**
+     * Prints the given string tree.
+     *
+     * @param pw the writer to be used to print the tree.
+     * @param l a string tree, i.e., a string list that can contain other string
+     *        lists, and so on recursively.
+     */
+    static void printList(final PrintWriter pw, final List<?> l) {
+        for (int i = 0; i < l.size(); ++i) {
+            Object o = l.get(i);
+            if (o instanceof List) {
+                printList(pw, (List<?>) o);
+            } else {
+                pw.print(o.toString());
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/Textifiable.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,83 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Label;
+
+/**
+ * An {@link jdk.internal.org.objectweb.asm.Attribute Attribute} that can print a readable
+ * representation of itself.
+ *
+ * Implementations should construct readable output from an attribute data
+ * structure. Such representation could be used in unit test assertions.
+ *
+ * @author Eugene Kuleshov
+ */
+public interface Textifiable {
+
+    /**
+     * Build a human readable representation of this attribute.
+     *
+     * @param buf a buffer used for printing Java code.
+     * @param labelNames map of label instances to their names.
+     */
+    void textify(StringBuffer buf, Map<Label, String> labelNames);
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/Textifier.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,1315 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.io.FileInputStream;
+import java.io.PrintWriter;
+import java.util.HashMap;
+import java.util.Map;
+
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassReader;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.Type;
+import jdk.internal.org.objectweb.asm.signature.SignatureReader;
+
+/**
+ * A {@link Printer} that prints a disassembled view of the classes it visits.
+ *
+ * @author Eric Bruneton
+ */
+public class Textifier extends Printer {
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for internal
+     * type names in bytecode notation.
+     */
+    public static final int INTERNAL_NAME = 0;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for field
+     * descriptors, formatted in bytecode notation
+     */
+    public static final int FIELD_DESCRIPTOR = 1;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for field
+     * signatures, formatted in bytecode notation
+     */
+    public static final int FIELD_SIGNATURE = 2;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for method
+     * descriptors, formatted in bytecode notation
+     */
+    public static final int METHOD_DESCRIPTOR = 3;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for method
+     * signatures, formatted in bytecode notation
+     */
+    public static final int METHOD_SIGNATURE = 4;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for class
+     * signatures, formatted in bytecode notation
+     */
+    public static final int CLASS_SIGNATURE = 5;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for field or
+     * method return value signatures, formatted in default Java notation
+     * (non-bytecode)
+     */
+    public static final int TYPE_DECLARATION = 6;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for class
+     * signatures, formatted in default Java notation (non-bytecode)
+     */
+    public static final int CLASS_DECLARATION = 7;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for method
+     * parameter signatures, formatted in default Java notation (non-bytecode)
+     */
+    public static final int PARAMETERS_DECLARATION = 8;
+
+    /**
+     * Constant used in {@link #appendDescriptor appendDescriptor} for handle
+     * descriptors, formatted in bytecode notation
+     */
+    public static final int HANDLE_DESCRIPTOR = 9;
+
+    /**
+     * Tab for class members.
+     */
+    protected String tab = "  ";
+
+    /**
+     * Tab for bytecode instructions.
+     */
+    protected String tab2 = "    ";
+
+    /**
+     * Tab for table and lookup switch instructions.
+     */
+    protected String tab3 = "      ";
+
+    /**
+     * Tab for labels.
+     */
+    protected String ltab = "   ";
+
+    /**
+     * The label names. This map associate String values to Label keys.
+     */
+    protected Map<Label, String> labelNames;
+
+    private int valueNumber = 0;
+
+    /**
+     * Constructs a new {@link Textifier}. <i>Subclasses must not use this
+     * constructor</i>. Instead, they must use the {@link #Textifier(int)}
+     * version.
+     */
+    public Textifier() {
+        this(Opcodes.ASM4);
+    }
+
+    /**
+     * Constructs a new {@link Textifier}.
+     *
+     * @param api the ASM API version implemented by this visitor. Must be one
+     *        of {@link Opcodes#ASM4}.
+     */
+    protected Textifier(final int api) {
+        super(api);
+    }
+
+    /**
+     * Prints a disassembled view of the given class to the standard output. <p>
+     * Usage: Textifier [-debug] &lt;binary class name or class
+     * file name &gt;
+     *
+     * @param args the command line arguments.
+     *
+     * @throws Exception if the class cannot be found, or if an IO exception
+     *         occurs.
+     */
+    public static void main(final String[] args) throws Exception {
+        int i = 0;
+        int flags = ClassReader.SKIP_DEBUG;
+
+        boolean ok = true;
+        if (args.length < 1 || args.length > 2) {
+            ok = false;
+        }
+        if (ok && "-debug".equals(args[0])) {
+            i = 1;
+            flags = 0;
+            if (args.length != 2) {
+                ok = false;
+            }
+        }
+        if (!ok) {
+            System.err.println("Prints a disassembled view of the given class.");
+            System.err.println("Usage: Textifier [-debug] "
+                    + "<fully qualified class name or class file name>");
+            return;
+        }
+        ClassReader cr;
+        if (args[i].endsWith(".class") || args[i].indexOf('\\') > -1
+                || args[i].indexOf('/') > -1)
+        {
+            cr = new ClassReader(new FileInputStream(args[i]));
+        } else {
+            cr = new ClassReader(args[i]);
+        }
+        cr.accept(new TraceClassVisitor(new PrintWriter(System.out)),
+                flags);
+    }
+
+    // ------------------------------------------------------------------------
+    // Classes
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        int major = version & 0xFFFF;
+        int minor = version >>> 16;
+        buf.setLength(0);
+        buf.append("// class version ")
+                .append(major)
+                .append('.')
+                .append(minor)
+                .append(" (")
+                .append(version)
+                .append(")\n");
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            buf.append("// DEPRECATED\n");
+        }
+        buf.append("// access flags 0x").append(Integer.toHexString(access).toUpperCase()).append('\n');
+
+        appendDescriptor(CLASS_SIGNATURE, signature);
+        if (signature != null) {
+            TraceSignatureVisitor sv = new TraceSignatureVisitor(access);
+            SignatureReader r = new SignatureReader(signature);
+            r.accept(sv);
+            buf.append("// declaration: ")
+                    .append(name)
+                    .append(sv.getDeclaration())
+                    .append('\n');
+        }
+
+        appendAccess(access & ~Opcodes.ACC_SUPER);
+        if ((access & Opcodes.ACC_ANNOTATION) != 0) {
+            buf.append("@interface ");
+        } else if ((access & Opcodes.ACC_INTERFACE) != 0) {
+            buf.append("interface ");
+        } else if ((access & Opcodes.ACC_ENUM) == 0) {
+            buf.append("class ");
+        }
+        appendDescriptor(INTERNAL_NAME, name);
+
+        if (superName != null && !"java/lang/Object".equals(superName)) {
+            buf.append(" extends ");
+            appendDescriptor(INTERNAL_NAME, superName);
+            buf.append(' ');
+        }
+        if (interfaces != null && interfaces.length > 0) {
+            buf.append(" implements ");
+            for (int i = 0; i < interfaces.length; ++i) {
+                appendDescriptor(INTERNAL_NAME, interfaces[i]);
+                buf.append(' ');
+            }
+        }
+        buf.append(" {\n\n");
+
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitSource(final String file, final String debug) {
+        buf.setLength(0);
+        if (file != null) {
+            buf.append(tab)
+                    .append("// compiled from: ")
+                    .append(file)
+                    .append('\n');
+        }
+        if (debug != null) {
+            buf.append(tab)
+                    .append("// debug info: ")
+                    .append(debug)
+                    .append('\n');
+        }
+        if (buf.length() > 0) {
+            text.add(buf.toString());
+        }
+    }
+
+    @Override
+    public void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append(tab).append("OUTERCLASS ");
+        appendDescriptor(INTERNAL_NAME, owner);
+        buf.append(' ');
+        if (name != null) {
+            buf.append(name).append(' ');
+        }
+        appendDescriptor(METHOD_DESCRIPTOR, desc);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public Textifier visitClassAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        text.add("\n");
+        return visitAnnotation(desc, visible);
+    }
+
+    @Override
+    public void visitClassAttribute(final Attribute attr) {
+        text.add("\n");
+        visitAttribute(attr);
+    }
+
+    @Override
+    public void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        buf.setLength(0);
+        buf.append(tab).append("// access flags 0x");
+        buf.append(Integer.toHexString(access & ~Opcodes.ACC_SUPER).toUpperCase()).append('\n');
+        buf.append(tab);
+        appendAccess(access);
+        buf.append("INNERCLASS ");
+        appendDescriptor(INTERNAL_NAME, name);
+        buf.append(' ');
+        appendDescriptor(INTERNAL_NAME, outerName);
+        buf.append(' ');
+        appendDescriptor(INTERNAL_NAME, innerName);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public Textifier visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        buf.setLength(0);
+        buf.append('\n');
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            buf.append(tab).append("// DEPRECATED\n");
+        }
+        buf.append(tab).append("// access flags 0x").append(Integer.toHexString(access).toUpperCase()).append('\n');
+        if (signature != null) {
+            buf.append(tab);
+            appendDescriptor(FIELD_SIGNATURE, signature);
+
+            TraceSignatureVisitor sv = new TraceSignatureVisitor(0);
+            SignatureReader r = new SignatureReader(signature);
+            r.acceptType(sv);
+            buf.append(tab)
+                    .append("// declaration: ")
+                    .append(sv.getDeclaration())
+                    .append('\n');
+        }
+
+        buf.append(tab);
+        appendAccess(access);
+
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append(' ').append(name);
+        if (value != null) {
+            buf.append(" = ");
+            if (value instanceof String) {
+                buf.append('\"').append(value).append('\"');
+            } else {
+                buf.append(value);
+            }
+        }
+
+        buf.append('\n');
+        text.add(buf.toString());
+
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        return t;
+    }
+
+    @Override
+    public Textifier visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        buf.setLength(0);
+        buf.append('\n');
+        if ((access & Opcodes.ACC_DEPRECATED) != 0) {
+            buf.append(tab).append("// DEPRECATED\n");
+        }
+        buf.append(tab).append("// access flags 0x").append(Integer.toHexString(access).toUpperCase()).append('\n');
+
+        if (signature != null) {
+            buf.append(tab);
+            appendDescriptor(METHOD_SIGNATURE, signature);
+
+            TraceSignatureVisitor v = new TraceSignatureVisitor(0);
+            SignatureReader r = new SignatureReader(signature);
+            r.accept(v);
+            String genericDecl = v.getDeclaration();
+            String genericReturn = v.getReturnType();
+            String genericExceptions = v.getExceptions();
+
+            buf.append(tab)
+                    .append("// declaration: ")
+                    .append(genericReturn)
+                    .append(' ')
+                    .append(name)
+                    .append(genericDecl);
+            if (genericExceptions != null) {
+                buf.append(" throws ").append(genericExceptions);
+            }
+            buf.append('\n');
+        }
+
+        buf.append(tab);
+        appendAccess(access);
+        if ((access & Opcodes.ACC_NATIVE) != 0) {
+            buf.append("native ");
+        }
+        if ((access & Opcodes.ACC_VARARGS) != 0) {
+            buf.append("varargs ");
+        }
+        if ((access & Opcodes.ACC_BRIDGE) != 0) {
+            buf.append("bridge ");
+        }
+
+        buf.append(name);
+        appendDescriptor(METHOD_DESCRIPTOR, desc);
+        if (exceptions != null && exceptions.length > 0) {
+            buf.append(" throws ");
+            for (int i = 0; i < exceptions.length; ++i) {
+                appendDescriptor(INTERNAL_NAME, exceptions[i]);
+                buf.append(' ');
+            }
+        }
+
+        buf.append('\n');
+        text.add(buf.toString());
+
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        return t;
+    }
+
+    @Override
+    public void visitClassEnd() {
+        text.add("}\n");
+    }
+
+    // ------------------------------------------------------------------------
+    // Annotations
+    // ------------------------------------------------------------------------
+
+    @Override
+    public void visit(final String name, final Object value) {
+        buf.setLength(0);
+        appendComa(valueNumber++);
+
+        if (name != null) {
+            buf.append(name).append('=');
+        }
+
+        if (value instanceof String) {
+            visitString((String) value);
+        } else if (value instanceof Type) {
+            visitType((Type) value);
+        } else if (value instanceof Byte) {
+            visitByte(((Byte) value).byteValue());
+        } else if (value instanceof Boolean) {
+            visitBoolean(((Boolean) value).booleanValue());
+        } else if (value instanceof Short) {
+            visitShort(((Short) value).shortValue());
+        } else if (value instanceof Character) {
+            visitChar(((Character) value).charValue());
+        } else if (value instanceof Integer) {
+            visitInt(((Integer) value).intValue());
+        } else if (value instanceof Float) {
+            visitFloat(((Float) value).floatValue());
+        } else if (value instanceof Long) {
+            visitLong(((Long) value).longValue());
+        } else if (value instanceof Double) {
+            visitDouble(((Double) value).doubleValue());
+        } else if (value.getClass().isArray()) {
+            buf.append('{');
+            if (value instanceof byte[]) {
+                byte[] v = (byte[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitByte(v[i]);
+                }
+            } else if (value instanceof boolean[]) {
+                boolean[] v = (boolean[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitBoolean(v[i]);
+                }
+            } else if (value instanceof short[]) {
+                short[] v = (short[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitShort(v[i]);
+                }
+            } else if (value instanceof char[]) {
+                char[] v = (char[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitChar(v[i]);
+                }
+            } else if (value instanceof int[]) {
+                int[] v = (int[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitInt(v[i]);
+                }
+            } else if (value instanceof long[]) {
+                long[] v = (long[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitLong(v[i]);
+                }
+            } else if (value instanceof float[]) {
+                float[] v = (float[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitFloat(v[i]);
+                }
+            } else if (value instanceof double[]) {
+                double[] v = (double[]) value;
+                for (int i = 0; i < v.length; i++) {
+                    appendComa(i);
+                    visitDouble(v[i]);
+                }
+            }
+            buf.append('}');
+        }
+
+        text.add(buf.toString());
+    }
+
+    private void visitInt(final int value) {
+        buf.append(value);
+    }
+
+    private void visitLong(final long value) {
+        buf.append(value).append('L');
+    }
+
+    private void visitFloat(final float value) {
+        buf.append(value).append('F');
+    }
+
+    private void visitDouble(final double value) {
+        buf.append(value).append('D');
+    }
+
+    private void visitChar(final char value) {
+        buf.append("(char)").append((int) value);
+    }
+
+    private void visitShort(final short value) {
+        buf.append("(short)").append(value);
+    }
+
+    private void visitByte(final byte value) {
+        buf.append("(byte)").append(value);
+    }
+
+    private void visitBoolean(final boolean value) {
+        buf.append(value);
+    }
+
+    private void visitString(final String value) {
+        appendString(buf, value);
+    }
+
+    private void visitType(final Type value) {
+        buf.append(value.getClassName()).append(".class");
+    }
+
+    @Override
+    public void visitEnum(
+        final String name,
+        final String desc,
+        final String value)
+    {
+        buf.setLength(0);
+        appendComa(valueNumber++);
+        if (name != null) {
+            buf.append(name).append('=');
+        }
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append('.').append(value);
+        text.add(buf.toString());
+    }
+
+    @Override
+    public Textifier visitAnnotation(
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        appendComa(valueNumber++);
+        if (name != null) {
+            buf.append(name).append('=');
+        }
+        buf.append('@');
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append('(');
+        text.add(buf.toString());
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        text.add(")");
+        return t;
+    }
+
+    @Override
+    public Textifier visitArray(
+        final String name)
+    {
+        buf.setLength(0);
+        appendComa(valueNumber++);
+        if (name != null) {
+            buf.append(name).append('=');
+        }
+        buf.append('{');
+        text.add(buf.toString());
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        text.add("}");
+        return t;
+    }
+
+    @Override
+    public void visitAnnotationEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Fields
+    // ------------------------------------------------------------------------
+
+    @Override
+    public Textifier visitFieldAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        return visitAnnotation(desc, visible);
+    }
+
+    @Override
+    public void visitFieldAttribute(final Attribute attr) {
+        visitAttribute(attr);
+    }
+
+    @Override
+    public void visitFieldEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Methods
+    // ------------------------------------------------------------------------
+
+    @Override
+    public Textifier visitAnnotationDefault() {
+        text.add(tab2 + "default=");
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        text.add("\n");
+        return t;
+    }
+
+    @Override
+    public Textifier visitMethodAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        return visitAnnotation(desc, visible);
+    }
+
+    @Override
+    public Textifier visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append('@');
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append('(');
+        text.add(buf.toString());
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        text.add(visible ? ") // parameter " : ") // invisible, parameter ");
+        text.add(new Integer(parameter));
+        text.add("\n");
+        return t;
+    }
+
+    @Override
+    public void visitMethodAttribute(final Attribute attr) {
+        buf.setLength(0);
+        buf.append(tab).append("ATTRIBUTE ");
+        appendDescriptor(-1, attr.type);
+
+        if (attr instanceof Textifiable) {
+            ((Textifiable) attr).textify(buf, labelNames);
+        } else {
+            buf.append(" : unknown\n");
+        }
+
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitCode() {
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        buf.setLength(0);
+        buf.append(ltab);
+        buf.append("FRAME ");
+        switch (type) {
+            case Opcodes.F_NEW:
+            case Opcodes.F_FULL:
+                buf.append("FULL [");
+                appendFrameTypes(nLocal, local);
+                buf.append("] [");
+                appendFrameTypes(nStack, stack);
+                buf.append(']');
+                break;
+            case Opcodes.F_APPEND:
+                buf.append("APPEND [");
+                appendFrameTypes(nLocal, local);
+                buf.append(']');
+                break;
+            case Opcodes.F_CHOP:
+                buf.append("CHOP ").append(nLocal);
+                break;
+            case Opcodes.F_SAME:
+                buf.append("SAME");
+                break;
+            case Opcodes.F_SAME1:
+                buf.append("SAME1 ");
+                appendFrameTypes(1, stack);
+                break;
+        }
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        buf.setLength(0);
+        buf.append(tab2).append(OPCODES[opcode]).append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        buf.setLength(0);
+        buf.append(tab2)
+                .append(OPCODES[opcode])
+                .append(' ')
+                .append(opcode == Opcodes.NEWARRAY
+                        ? TYPES[operand]
+                        : Integer.toString(operand))
+                .append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        buf.setLength(0);
+        buf.append(tab2)
+                .append(OPCODES[opcode])
+                .append(' ')
+                .append(var)
+                .append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        buf.setLength(0);
+        buf.append(tab2).append(OPCODES[opcode]).append(' ');
+        appendDescriptor(INTERNAL_NAME, type);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append(OPCODES[opcode]).append(' ');
+        appendDescriptor(INTERNAL_NAME, owner);
+        buf.append('.').append(name).append(" : ");
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append(OPCODES[opcode]).append(' ');
+        appendDescriptor(INTERNAL_NAME, owner);
+        buf.append('.').append(name).append(' ');
+        appendDescriptor(METHOD_DESCRIPTOR, desc);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append("INVOKEDYNAMIC").append(' ');
+        buf.append(name);
+        appendDescriptor(METHOD_DESCRIPTOR, desc);
+        buf.append(" [");
+        appendHandle(bsm);
+        buf.append(tab3).append("// arguments:");
+        if(bsmArgs.length == 0) {
+            buf.append(" none");
+        } else {
+            buf.append('\n').append(tab3);
+            for(int i = 0; i < bsmArgs.length; i++) {
+                Object cst = bsmArgs[i];
+                if (cst instanceof String) {
+                    Printer.appendString(buf, (String) cst);
+                } else if (cst instanceof Type) {
+                    buf.append(((Type) cst).getDescriptor()).append(".class");
+                } else if (cst instanceof Handle) {
+                    appendHandle((Handle) cst);
+                } else {
+                    buf.append(cst);
+                }
+                buf.append(", ");
+            }
+            buf.setLength(buf.length() - 2);
+        }
+        buf.append('\n');
+        buf.append(tab2).append("]\n");
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        buf.setLength(0);
+        buf.append(tab2).append(OPCODES[opcode]).append(' ');
+        appendLabel(label);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        buf.setLength(0);
+        buf.append(ltab);
+        appendLabel(label);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        buf.setLength(0);
+        buf.append(tab2).append("LDC ");
+        if (cst instanceof String) {
+            Printer.appendString(buf, (String) cst);
+        } else if (cst instanceof Type) {
+            buf.append(((Type) cst).getDescriptor()).append(".class");
+        } else {
+            buf.append(cst);
+        }
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        buf.setLength(0);
+        buf.append(tab2)
+                .append("IINC ")
+                .append(var)
+                .append(' ')
+                .append(increment)
+                .append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append("TABLESWITCH\n");
+        for (int i = 0; i < labels.length; ++i) {
+            buf.append(tab3).append(min + i).append(": ");
+            appendLabel(labels[i]);
+            buf.append('\n');
+        }
+        buf.append(tab3).append("default: ");
+        appendLabel(dflt);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append("LOOKUPSWITCH\n");
+        for (int i = 0; i < labels.length; ++i) {
+            buf.append(tab3).append(keys[i]).append(": ");
+            appendLabel(labels[i]);
+            buf.append('\n');
+        }
+        buf.append(tab3).append("default: ");
+        appendLabel(dflt);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        buf.setLength(0);
+        buf.append(tab2).append("MULTIANEWARRAY ");
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append(' ').append(dims).append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append("TRYCATCHBLOCK ");
+        appendLabel(start);
+        buf.append(' ');
+        appendLabel(end);
+        buf.append(' ');
+        appendLabel(handler);
+        buf.append(' ');
+        appendDescriptor(INTERNAL_NAME, type);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        buf.setLength(0);
+        buf.append(tab2).append("LOCALVARIABLE ").append(name).append(' ');
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append(' ');
+        appendLabel(start);
+        buf.append(' ');
+        appendLabel(end);
+        buf.append(' ').append(index).append('\n');
+
+        if (signature != null) {
+            buf.append(tab2);
+            appendDescriptor(FIELD_SIGNATURE, signature);
+
+            TraceSignatureVisitor sv = new TraceSignatureVisitor(0);
+            SignatureReader r = new SignatureReader(signature);
+            r.acceptType(sv);
+            buf.append(tab2)
+                    .append("// declaration: ")
+                    .append(sv.getDeclaration())
+                    .append('\n');
+        }
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitLineNumber(final int line, final Label start) {
+        buf.setLength(0);
+        buf.append(tab2).append("LINENUMBER ").append(line).append(' ');
+        appendLabel(start);
+        buf.append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        buf.setLength(0);
+        buf.append(tab2).append("MAXSTACK = ").append(maxStack).append('\n');
+        text.add(buf.toString());
+
+        buf.setLength(0);
+        buf.append(tab2).append("MAXLOCALS = ").append(maxLocals).append('\n');
+        text.add(buf.toString());
+    }
+
+    @Override
+    public void visitMethodEnd() {
+    }
+
+    // ------------------------------------------------------------------------
+    // Common methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Prints a disassembled view of the given annotation.
+     *
+     * @param desc the class descriptor of the annotation class.
+     * @param visible <tt>true</tt> if the annotation is visible at runtime.
+     * @return a visitor to visit the annotation values.
+     */
+    public Textifier visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        buf.setLength(0);
+        buf.append(tab).append('@');
+        appendDescriptor(FIELD_DESCRIPTOR, desc);
+        buf.append('(');
+        text.add(buf.toString());
+        Textifier t = createTextifier();
+        text.add(t.getText());
+        text.add(visible ? ")\n" : ") // invisible\n");
+        return t;
+    }
+
+    /**
+     * Prints a disassembled view of the given attribute.
+     *
+     * @param attr an attribute.
+     */
+    public void visitAttribute(final Attribute attr) {
+        buf.setLength(0);
+        buf.append(tab).append("ATTRIBUTE ");
+        appendDescriptor(-1, attr.type);
+
+        if (attr instanceof Textifiable) {
+            ((Textifiable) attr).textify(buf, null);
+        } else {
+            buf.append(" : unknown\n");
+        }
+
+        text.add(buf.toString());
+    }
+
+    // ------------------------------------------------------------------------
+    // Utility methods
+    // ------------------------------------------------------------------------
+
+    /**
+     * Creates a new TraceVisitor instance.
+     *
+     * @return a new TraceVisitor.
+     */
+    protected Textifier createTextifier() {
+        return new Textifier();
+    }
+
+    /**
+     * Appends an internal name, a type descriptor or a type signature to
+     * {@link #buf buf}.
+     *
+     * @param type indicates if desc is an internal name, a field descriptor, a
+     *        method descriptor, a class signature, ...
+     * @param desc an internal name, type descriptor, or type signature. May be
+     *        <tt>null</tt>.
+     */
+    protected void appendDescriptor(final int type, final String desc) {
+        if (type == CLASS_SIGNATURE || type == FIELD_SIGNATURE
+                || type == METHOD_SIGNATURE)
+        {
+            if (desc != null) {
+                buf.append("// signature ").append(desc).append('\n');
+            }
+        } else {
+            buf.append(desc);
+        }
+    }
+
+    /**
+     * Appends the name of the given label to {@link #buf buf}. Creates a new
+     * label name if the given label does not yet have one.
+     *
+     * @param l a label.
+     */
+    protected void appendLabel(final Label l) {
+        if (labelNames == null) {
+            labelNames = new HashMap<Label, String>();
+        }
+        String name = labelNames.get(l);
+        if (name == null) {
+            name = "L" + labelNames.size();
+            labelNames.put(l, name);
+        }
+        buf.append(name);
+    }
+
+    /**
+     * Appends the information about the given handle to {@link #buf buf}.
+     *
+     * @param h a handle, non null.
+     */
+    protected void appendHandle(final Handle h) {
+        buf.append('\n').append(tab3);
+        int tag = h.getTag();
+        buf.append("// handle kind 0x").append(Integer.toHexString(tag)).append(" : ");
+        switch (tag) {
+            case Opcodes.H_GETFIELD:
+                buf.append("GETFIELD");
+                break;
+            case Opcodes.H_GETSTATIC:
+                buf.append("GETSTATIC");
+                break;
+            case Opcodes.H_PUTFIELD:
+                buf.append("PUTFIELD");
+                break;
+            case Opcodes.H_PUTSTATIC:
+                buf.append("PUTSTATIC");
+                break;
+            case Opcodes.H_INVOKEINTERFACE:
+                buf.append("INVOKEINTERFACE");
+                break;
+            case Opcodes.H_INVOKESPECIAL:
+                buf.append("INVOKESPECIAL");
+                break;
+            case Opcodes.H_INVOKESTATIC:
+                buf.append("INVOKESTATIC");
+                break;
+            case Opcodes.H_INVOKEVIRTUAL:
+                buf.append("INVOKEVIRTUAL");
+                break;
+            case Opcodes.H_NEWINVOKESPECIAL:
+                buf.append("NEWINVOKESPECIAL");
+                break;
+        }
+        buf.append('\n');
+        buf.append(tab3);
+        appendDescriptor(INTERNAL_NAME, h.getOwner());
+        buf.append('.');
+        buf.append(h.getName());
+        buf.append('(');
+        appendDescriptor(HANDLE_DESCRIPTOR, h.getDesc());
+        buf.append(')').append('\n');
+    }
+
+    /**
+     * Appends a string representation of the given access modifiers to {@link
+     * #buf buf}.
+     *
+     * @param access some access modifiers.
+     */
+    private void appendAccess(final int access) {
+        if ((access & Opcodes.ACC_PUBLIC) != 0) {
+            buf.append("public ");
+        }
+        if ((access & Opcodes.ACC_PRIVATE) != 0) {
+            buf.append("private ");
+        }
+        if ((access & Opcodes.ACC_PROTECTED) != 0) {
+            buf.append("protected ");
+        }
+        if ((access & Opcodes.ACC_FINAL) != 0) {
+            buf.append("final ");
+        }
+        if ((access & Opcodes.ACC_STATIC) != 0) {
+            buf.append("static ");
+        }
+        if ((access & Opcodes.ACC_SYNCHRONIZED) != 0) {
+            buf.append("synchronized ");
+        }
+        if ((access & Opcodes.ACC_VOLATILE) != 0) {
+            buf.append("volatile ");
+        }
+        if ((access & Opcodes.ACC_TRANSIENT) != 0) {
+            buf.append("transient ");
+        }
+        if ((access & Opcodes.ACC_ABSTRACT) != 0) {
+            buf.append("abstract ");
+        }
+        if ((access & Opcodes.ACC_STRICT) != 0) {
+            buf.append("strictfp ");
+        }
+        if ((access & Opcodes.ACC_ENUM) != 0) {
+            buf.append("enum ");
+        }
+    }
+
+    private void appendComa(final int i) {
+        if (i != 0) {
+            buf.append(", ");
+        }
+    }
+
+    private void appendFrameTypes(final int n, final Object[] o) {
+        for (int i = 0; i < n; ++i) {
+            if (i > 0) {
+                buf.append(' ');
+            }
+            if (o[i] instanceof String) {
+                String desc = (String) o[i];
+                if (desc.startsWith("[")) {
+                    appendDescriptor(FIELD_DESCRIPTOR, desc);
+                } else {
+                    appendDescriptor(INTERNAL_NAME, desc);
+                }
+            } else if (o[i] instanceof Integer) {
+                switch (((Integer) o[i]).intValue()) {
+                    case 0:
+                        appendDescriptor(FIELD_DESCRIPTOR, "T");
+                        break;
+                    case 1:
+                        appendDescriptor(FIELD_DESCRIPTOR, "I");
+                        break;
+                    case 2:
+                        appendDescriptor(FIELD_DESCRIPTOR, "F");
+                        break;
+                    case 3:
+                        appendDescriptor(FIELD_DESCRIPTOR, "D");
+                        break;
+                    case 4:
+                        appendDescriptor(FIELD_DESCRIPTOR, "J");
+                        break;
+                    case 5:
+                        appendDescriptor(FIELD_DESCRIPTOR, "N");
+                        break;
+                    case 6:
+                        appendDescriptor(FIELD_DESCRIPTOR, "U");
+                        break;
+                }
+            } else {
+                appendLabel((Label) o[i]);
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/TraceAnnotationVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,125 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * An {@link AnnotationVisitor} that prints the annotations it visits with a
+ * {@link Printer}.
+ *
+ * @author Eric Bruneton
+ */
+public final class TraceAnnotationVisitor extends AnnotationVisitor {
+
+    private final Printer p;
+
+    public TraceAnnotationVisitor(final Printer p) {
+        this(null, p);
+    }
+
+    public TraceAnnotationVisitor(final AnnotationVisitor av, final Printer p) {
+        super(Opcodes.ASM4, av);
+        this.p = p;
+    }
+
+    @Override
+    public void visit(final String name, final Object value) {
+        p.visit(name, value);
+        super.visit(name, value);
+    }
+
+    @Override
+    public void visitEnum(
+        final String name,
+        final String desc,
+        final String value)
+    {
+        p.visitEnum(name, desc, value);
+        super.visitEnum(name, desc, value);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String name,
+        final String desc)
+    {
+        Printer p = this.p.visitAnnotation(name, desc);
+        AnnotationVisitor av = this.av == null
+                ? null
+                : this.av.visitAnnotation(name, desc);
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public AnnotationVisitor visitArray(final String name) {
+        Printer p = this.p.visitArray(name);
+        AnnotationVisitor av = this.av == null
+                ? null
+                : this.av.visitArray(name);
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public void visitEnd() {
+        p.visitAnnotationEnd();
+        super.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/TraceClassVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,262 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import java.io.PrintWriter;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.ClassVisitor;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link ClassVisitor} that prints the classes it visits with a
+ * {@link Printer}. This class visitor can be used in the middle of a class
+ * visitor chain to trace the class that is visited at a given point in this
+ * chain. This may be useful for debugging purposes. <p> The trace printed when
+ * visiting the <tt>Hello</tt> class is the following: <p> <blockquote>
+ *
+ * <pre> // class version 49.0 (49) // access flags 0x21 public class Hello {
+ *
+ * // compiled from: Hello.java
+ *
+ * // access flags 0x1 public &lt;init&gt; ()V ALOAD 0 INVOKESPECIAL
+ * java/lang/Object &lt;init&gt; ()V RETURN MAXSTACK = 1 MAXLOCALS = 1
+ *
+ * // access flags 0x9 public static main ([Ljava/lang/String;)V GETSTATIC
+ * java/lang/System out Ljava/io/PrintStream; LDC &quot;hello&quot;
+ * INVOKEVIRTUAL java/io/PrintStream println (Ljava/lang/String;)V RETURN
+ * MAXSTACK = 2 MAXLOCALS = 1 } </pre>
+ *
+ * </blockquote> where <tt>Hello</tt> is defined by: <p> <blockquote>
+ *
+ * <pre> public class Hello {
+ *
+ * public static void main(String[] args) {
+ * System.out.println(&quot;hello&quot;); } } </pre>
+ *
+ * </blockquote>
+ *
+ * @author Eric Bruneton
+ * @author Eugene Kuleshov
+ */
+public final class TraceClassVisitor extends ClassVisitor {
+
+    /**
+     * The print writer to be used to print the class. May be null.
+     */
+    private final PrintWriter pw;
+
+    /**
+     * The object that actually converts visit events into text.
+     */
+    public final Printer p;
+
+    /**
+     * Constructs a new {@link TraceClassVisitor}.
+     *
+     * @param pw the print writer to be used to print the class.
+     */
+    public TraceClassVisitor(final PrintWriter pw) {
+        this(null, pw);
+    }
+
+    /**
+     * Constructs a new {@link TraceClassVisitor}.
+     *
+     * @param cv the {@link ClassVisitor} to which this visitor delegates calls.
+     *        May be <tt>null</tt>.
+     * @param pw the print writer to be used to print the class.
+     */
+    public TraceClassVisitor(final ClassVisitor cv, final PrintWriter pw) {
+        this(cv, new Textifier(), pw);
+    }
+
+    /**
+     * Constructs a new {@link TraceClassVisitor}.
+     *
+     * @param cv the {@link ClassVisitor} to which this visitor delegates calls.
+     *        May be <tt>null</tt>.
+     * @param p the object that actually converts visit events into text.
+     * @param pw the print writer to be used to print the class. May be null if
+     *        you simply want to use the result via
+     *        {@link Printer#getText()}, instead of printing it.
+     */
+    public TraceClassVisitor(
+        final ClassVisitor cv,
+        final Printer p,
+        final PrintWriter pw)
+    {
+        super(Opcodes.ASM4, cv);
+        this.pw = pw;
+        this.p = p;
+    }
+
+    @Override
+    public void visit(
+        final int version,
+        final int access,
+        final String name,
+        final String signature,
+        final String superName,
+        final String[] interfaces)
+    {
+        p.visit(version, access, name, signature, superName, interfaces);
+        super.visit(version, access, name, signature, superName, interfaces);
+    }
+
+    @Override
+    public void visitSource(final String file, final String debug) {
+        p.visitSource(file, debug);
+        super.visitSource(file, debug);
+    }
+
+    @Override
+    public void visitOuterClass(
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        p.visitOuterClass(owner, name, desc);
+        super.visitOuterClass(owner, name, desc);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        Printer p = this.p.visitClassAnnotation(desc, visible);
+        AnnotationVisitor av = cv == null ? null : cv.visitAnnotation(desc,
+                visible);
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        p.visitClassAttribute(attr);
+        super.visitAttribute(attr);
+    }
+
+    @Override
+    public void visitInnerClass(
+        final String name,
+        final String outerName,
+        final String innerName,
+        final int access)
+    {
+        p.visitInnerClass(name, outerName, innerName, access);
+        super.visitInnerClass(name, outerName, innerName, access);
+    }
+
+    @Override
+    public FieldVisitor visitField(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final Object value)
+    {
+        Printer p = this.p.visitField(access,
+                name,
+                desc,
+                signature,
+                value);
+        FieldVisitor fv = cv == null ? null : cv.visitField(access,
+                name,
+                desc,
+                signature,
+                value);
+        return new TraceFieldVisitor(fv, p);
+    }
+
+    @Override
+    public MethodVisitor visitMethod(
+        final int access,
+        final String name,
+        final String desc,
+        final String signature,
+        final String[] exceptions)
+    {
+        Printer p = this.p.visitMethod(access,
+                name,
+                desc,
+                signature,
+                exceptions);
+        MethodVisitor mv = cv == null ? null : cv.visitMethod(access,
+                name,
+                desc,
+                signature,
+                exceptions);
+        return new TraceMethodVisitor(mv, p);
+    }
+
+    @Override
+    public void visitEnd() {
+        p.visitClassEnd();
+        if (pw != null) {
+            p.print(pw);
+            pw.flush();
+        }
+        super.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/TraceFieldVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,108 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.FieldVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link FieldVisitor} that prints the fields it visits with a
+ * {@link Printer}.
+ *
+ * @author Eric Bruneton
+ */
+public final class TraceFieldVisitor extends FieldVisitor {
+
+    public final Printer p;
+
+    public TraceFieldVisitor(final Printer p) {
+        this(null, p);
+    }
+
+    public TraceFieldVisitor(final FieldVisitor fv, final Printer p) {
+        super(Opcodes.ASM4, fv);
+        this.p = p;
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        Printer p = this.p.visitFieldAnnotation(desc, visible);
+        AnnotationVisitor av = fv == null ? null : fv.visitAnnotation(desc,
+                visible);
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        p.visitFieldAttribute(attr);
+        super.visitAttribute(attr);
+    }
+
+    @Override
+    public void visitEnd() {
+        p.visitFieldEnd();
+        super.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/TraceMethodVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,294 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * Copyright (c) 2011 Google
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.AnnotationVisitor;
+import jdk.internal.org.objectweb.asm.Attribute;
+import jdk.internal.org.objectweb.asm.Handle;
+import jdk.internal.org.objectweb.asm.Label;
+import jdk.internal.org.objectweb.asm.MethodVisitor;
+import jdk.internal.org.objectweb.asm.Opcodes;
+
+/**
+ * A {@link MethodVisitor} that prints the methods it visits with a
+ * {@link Printer}.
+ *
+ * @author Eric Bruneton
+ */
+public final class TraceMethodVisitor extends MethodVisitor {
+
+    public final Printer p;
+
+    public TraceMethodVisitor(final Printer p) {
+        this(null, p);
+    }
+
+    public TraceMethodVisitor(final MethodVisitor mv, final Printer p) {
+        super(Opcodes.ASM4, mv);
+        this.p = p;
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotation(
+        final String desc,
+        final boolean visible)
+    {
+        Printer p = this.p.visitMethodAnnotation(desc, visible);
+        AnnotationVisitor av = mv == null ? null : mv.visitAnnotation(desc,
+                visible);
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public void visitAttribute(final Attribute attr) {
+        p.visitMethodAttribute(attr);
+        super.visitAttribute(attr);
+    }
+
+    @Override
+    public AnnotationVisitor visitAnnotationDefault() {
+        Printer p = this.p.visitAnnotationDefault();
+        AnnotationVisitor av = mv == null ? null : mv.visitAnnotationDefault();
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public AnnotationVisitor visitParameterAnnotation(
+        final int parameter,
+        final String desc,
+        final boolean visible)
+    {
+        Printer p = this.p.visitParameterAnnotation(parameter,
+                desc,
+                visible);
+        AnnotationVisitor av = mv == null
+                ? null
+                : mv.visitParameterAnnotation(parameter, desc, visible);
+        return new TraceAnnotationVisitor(av, p);
+    }
+
+    @Override
+    public void visitCode() {
+        p.visitCode();
+        super.visitCode();
+    }
+
+    @Override
+    public void visitFrame(
+        final int type,
+        final int nLocal,
+        final Object[] local,
+        final int nStack,
+        final Object[] stack)
+    {
+        p.visitFrame(type, nLocal, local, nStack, stack);
+        super.visitFrame(type, nLocal, local, nStack, stack);
+    }
+
+    @Override
+    public void visitInsn(final int opcode) {
+        p.visitInsn(opcode);
+        super.visitInsn(opcode);
+    }
+
+    @Override
+    public void visitIntInsn(final int opcode, final int operand) {
+        p.visitIntInsn(opcode, operand);
+        super.visitIntInsn(opcode, operand);
+    }
+
+    @Override
+    public void visitVarInsn(final int opcode, final int var) {
+        p.visitVarInsn(opcode, var);
+        super.visitVarInsn(opcode, var);
+    }
+
+    @Override
+    public void visitTypeInsn(final int opcode, final String type) {
+        p.visitTypeInsn(opcode, type);
+        super.visitTypeInsn(opcode, type);
+    }
+
+    @Override
+    public void visitFieldInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        p.visitFieldInsn(opcode, owner, name, desc);
+        super.visitFieldInsn(opcode, owner, name, desc);
+    }
+
+    @Override
+    public void visitMethodInsn(
+        final int opcode,
+        final String owner,
+        final String name,
+        final String desc)
+    {
+        p.visitMethodInsn(opcode, owner, name, desc);
+        super.visitMethodInsn(opcode, owner, name, desc);
+    }
+
+    @Override
+    public void visitInvokeDynamicInsn(
+        String name,
+        String desc,
+        Handle bsm,
+        Object... bsmArgs)
+    {
+        p.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+        super.visitInvokeDynamicInsn(name, desc, bsm, bsmArgs);
+    }
+
+    @Override
+    public void visitJumpInsn(final int opcode, final Label label) {
+        p.visitJumpInsn(opcode, label);
+        super.visitJumpInsn(opcode, label);
+    }
+
+    @Override
+    public void visitLabel(final Label label) {
+        p.visitLabel(label);
+        super.visitLabel(label);
+    }
+
+    @Override
+    public void visitLdcInsn(final Object cst) {
+        p.visitLdcInsn(cst);
+        super.visitLdcInsn(cst);
+    }
+
+    @Override
+    public void visitIincInsn(final int var, final int increment) {
+        p.visitIincInsn(var, increment);
+        super.visitIincInsn(var, increment);
+    }
+
+    @Override
+    public void visitTableSwitchInsn(
+        final int min,
+        final int max,
+        final Label dflt,
+        final Label... labels)
+    {
+        p.visitTableSwitchInsn(min, max, dflt, labels);
+        super.visitTableSwitchInsn(min, max, dflt, labels);
+    }
+
+    @Override
+    public void visitLookupSwitchInsn(
+        final Label dflt,
+        final int[] keys,
+        final Label[] labels)
+    {
+        p.visitLookupSwitchInsn(dflt, keys, labels);
+        super.visitLookupSwitchInsn(dflt, keys, labels);
+    }
+
+    @Override
+    public void visitMultiANewArrayInsn(final String desc, final int dims) {
+        p.visitMultiANewArrayInsn(desc, dims);
+        super.visitMultiANewArrayInsn(desc, dims);
+    }
+
+    @Override
+    public void visitTryCatchBlock(
+        final Label start,
+        final Label end,
+        final Label handler,
+        final String type)
+    {
+        p.visitTryCatchBlock(start, end, handler, type);
+        super.visitTryCatchBlock(start, end, handler, type);
+    }
+
+    @Override
+    public void visitLocalVariable(
+        final String name,
+        final String desc,
+        final String signature,
+        final Label start,
+        final Label end,
+        final int index)
+    {
+        p.visitLocalVariable(name, desc, signature, start, end, index);
+        super.visitLocalVariable(name, desc, signature, start, end, index);
+    }
+
+    @Override
+    public void visitLineNumber(final int line, final Label start) {
+        p.visitLineNumber(line, start);
+        super.visitLineNumber(line, start);
+    }
+
+    @Override
+    public void visitMaxs(final int maxStack, final int maxLocals) {
+        p.visitMaxs(maxStack, maxLocals);
+        super.visitMaxs(maxStack, maxLocals);
+    }
+
+    @Override
+    public void visitEnd() {
+        p.visitMethodEnd();
+        super.visitEnd();
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/jdk/internal/org/objectweb/asm/util/TraceSignatureVisitor.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,347 @@
+/*
+ * 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.
+ */
+
+/*
+ * This file is available under and governed by the GNU General Public
+ * License version 2 only, as published by the Free Software Foundation.
+ * However, the following notice accompanied the original version of this
+ * file:
+ *
+ * ASM: a very small and fast Java bytecode manipulation framework
+ * Copyright (c) 2000-2011 INRIA, France Telecom
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of the copyright holders nor the names of its
+ *    contributors may be used to endorse or promote products derived from
+ *    this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+package jdk.internal.org.objectweb.asm.util;
+
+import jdk.internal.org.objectweb.asm.Opcodes;
+import jdk.internal.org.objectweb.asm.signature.SignatureVisitor;
+
+/**
+ * A {@link SignatureVisitor} that prints a disassembled view of the signature
+ * it visits.
+ *
+ * @author Eugene Kuleshov
+ * @author Eric Bruneton
+ */
+public final class TraceSignatureVisitor extends SignatureVisitor {
+
+    private final StringBuffer declaration;
+
+    private boolean isInterface;
+
+    private boolean seenFormalParameter;
+
+    private boolean seenInterfaceBound;
+
+    private boolean seenParameter;
+
+    private boolean seenInterface;
+
+    private StringBuffer returnType;
+
+    private StringBuffer exceptions;
+
+    /**
+     * Stack used to keep track of class types that have arguments. Each element
+     * of this stack is a boolean encoded in one bit. The top of the stack is
+     * the lowest order bit. Pushing false = *2, pushing true = *2+1, popping =
+     * /2.
+     */
+    private int argumentStack;
+
+    /**
+     * Stack used to keep track of array class types. Each element of this stack
+     * is a boolean encoded in one bit. The top of the stack is the lowest order
+     * bit. Pushing false = *2, pushing true = *2+1, popping = /2.
+     */
+    private int arrayStack;
+
+    private String separator = "";
+
+    public TraceSignatureVisitor(final int access) {
+        super(Opcodes.ASM4);
+        isInterface = (access & Opcodes.ACC_INTERFACE) != 0;
+        this.declaration = new StringBuffer();
+    }
+
+    private TraceSignatureVisitor(final StringBuffer buf) {
+        super(Opcodes.ASM4);
+        this.declaration = buf;
+    }
+
+    @Override
+    public void visitFormalTypeParameter(final String name) {
+        declaration.append(seenFormalParameter ? ", " : "<").append(name);
+        seenFormalParameter = true;
+        seenInterfaceBound = false;
+    }
+
+    @Override
+    public SignatureVisitor visitClassBound() {
+        separator = " extends ";
+        startType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitInterfaceBound() {
+        separator = seenInterfaceBound ? ", " : " extends ";
+        seenInterfaceBound = true;
+        startType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitSuperclass() {
+        endFormals();
+        separator = " extends ";
+        startType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitInterface() {
+        separator = seenInterface ? ", " : isInterface
+                ? " extends "
+                : " implements ";
+        seenInterface = true;
+        startType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitParameterType() {
+        endFormals();
+        if (seenParameter) {
+            declaration.append(", ");
+        } else {
+            seenParameter = true;
+            declaration.append('(');
+        }
+        startType();
+        return this;
+    }
+
+    @Override
+    public SignatureVisitor visitReturnType() {
+        endFormals();
+        if (seenParameter) {
+            seenParameter = false;
+        } else {
+            declaration.append('(');
+        }
+        declaration.append(')');
+        returnType = new StringBuffer();
+        return new TraceSignatureVisitor(returnType);
+    }
+
+    @Override
+    public SignatureVisitor visitExceptionType() {
+        if (exceptions == null) {
+            exceptions = new StringBuffer();
+        } else {
+            exceptions.append(", ");
+        }
+        // startType();
+        return new TraceSignatureVisitor(exceptions);
+    }
+
+    @Override
+    public void visitBaseType(final char descriptor) {
+        switch (descriptor) {
+            case 'V':
+                declaration.append("void");
+                break;
+            case 'B':
+                declaration.append("byte");
+                break;
+            case 'J':
+                declaration.append("long");
+                break;
+            case 'Z':
+                declaration.append("boolean");
+                break;
+            case 'I':
+                declaration.append("int");
+                break;
+            case 'S':
+                declaration.append("short");
+                break;
+            case 'C':
+                declaration.append("char");
+                break;
+            case 'F':
+                declaration.append("float");
+                break;
+            // case 'D':
+            default:
+                declaration.append("double");
+                break;
+        }
+        endType();
+    }
+
+    @Override
+    public void visitTypeVariable(final String name) {
+        declaration.append(name);
+        endType();
+    }
+
+    @Override
+    public SignatureVisitor visitArrayType() {
+        startType();
+        arrayStack |= 1;
+        return this;
+    }
+
+    @Override
+    public void visitClassType(final String name) {
+        if ("java/lang/Object".equals(name)) {
+            // Map<java.lang.Object,java.util.List>
+            // or
+            // abstract public V get(Object key); (seen in Dictionary.class)
+            // should have Object
+            // but java.lang.String extends java.lang.Object is unnecessary
+            boolean needObjectClass = argumentStack % 2 != 0 || seenParameter;
+            if (needObjectClass) {
+                declaration.append(separator).append(name.replace('/', '.'));
+            }
+        } else {
+            declaration.append(separator).append(name.replace('/', '.'));
+        }
+        separator = "";
+        argumentStack *= 2;
+    }
+
+    @Override
+    public void visitInnerClassType(final String name) {
+        if (argumentStack % 2 != 0) {
+            declaration.append('>');
+        }
+        argumentStack /= 2;
+        declaration.append('.');
+        declaration.append(separator).append(name.replace('/', '.'));
+        separator = "";
+        argumentStack *= 2;
+    }
+
+    @Override
+    public void visitTypeArgument() {
+        if (argumentStack % 2 == 0) {
+            ++argumentStack;
+            declaration.append('<');
+        } else {
+            declaration.append(", ");
+        }
+        declaration.append('?');
+    }
+
+    @Override
+    public SignatureVisitor visitTypeArgument(final char tag) {
+        if (argumentStack % 2 == 0) {
+            ++argumentStack;
+            declaration.append('<');
+        } else {
+            declaration.append(", ");
+        }
+
+        if (tag == EXTENDS) {
+            declaration.append("? extends ");
+        } else if (tag == SUPER) {
+            declaration.append("? super ");
+        }
+
+        startType();
+        return this;
+    }
+
+    @Override
+    public void visitEnd() {
+        if (argumentStack % 2 != 0) {
+            declaration.append('>');
+        }
+        argumentStack /= 2;
+        endType();
+    }
+
+    public String getDeclaration() {
+        return declaration.toString();
+    }
+
+    public String getReturnType() {
+        return returnType == null ? null : returnType.toString();
+    }
+
+    public String getExceptions() {
+        return exceptions == null ? null : exceptions.toString();
+    }
+
+    // -----------------------------------------------
+
+    private void endFormals() {
+        if (seenFormalParameter) {
+            declaration.append('>');
+            seenFormalParameter = false;
+        }
+    }
+
+    private void startType() {
+        arrayStack *= 2;
+    }
+
+    private void endType() {
+        if (arrayStack % 2 == 0) {
+            arrayStack /= 2;
+        } else {
+            while (arrayStack % 2 != 0) {
+                arrayStack /= 2;
+                declaration.append("[]");
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/awt/im/ExecutableInputMethodManager.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,632 @@
+/*
+ * Copyright (c) 1998, 2003, 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.awt.im;
+
+import java.awt.AWTException;
+import java.awt.CheckboxMenuItem;
+import java.awt.Component;
+import java.awt.Dialog;
+import java.awt.EventQueue;
+import java.awt.Frame;
+import java.awt.PopupMenu;
+import java.awt.Menu;
+import java.awt.MenuItem;
+import java.awt.Toolkit;
+import sun.awt.AppContext;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import java.awt.event.InvocationEvent;
+import java.awt.im.spi.InputMethodDescriptor;
+import java.lang.reflect.InvocationTargetException;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.security.PrivilegedActionException;
+import java.security.PrivilegedExceptionAction;
+import java.util.Hashtable;
+import java.util.Iterator;
+import java.util.Locale;
+import java.util.ServiceLoader;
+import java.util.Vector;
+import java.util.Set;
+import java.util.prefs.BackingStoreException;
+import java.util.prefs.Preferences;
+import sun.awt.InputMethodSupport;
+import sun.awt.SunToolkit;
+
+/**
+ * <code>ExecutableInputMethodManager</code> is the implementation of the
+ * <code>InputMethodManager</code> class. It is runnable as a separate
+ * thread in the AWT environment.&nbsp;
+ * <code>InputMethodManager.getInstance()</code> creates an instance of
+ * <code>ExecutableInputMethodManager</code> and executes it as a deamon
+ * thread.
+ *
+ * @see InputMethodManager
+ */
+class ExecutableInputMethodManager extends InputMethodManager
+                                   implements Runnable
+{
+    // the input context that's informed about selections from the user interface
+    private InputContext currentInputContext;
+
+    // Menu item string for the trigger menu.
+    private String triggerMenuString;
+
+    // popup menu for selecting an input method
+    private InputMethodPopupMenu selectionMenu;
+    private static String selectInputMethodMenuTitle;
+
+    // locator and name of host adapter
+    private InputMethodLocator hostAdapterLocator;
+
+    // locators for Java input methods
+    private int javaInputMethodCount;         // number of Java input methods found
+    private Vector<InputMethodLocator> javaInputMethodLocatorList;
+
+    // component that is requesting input method switch
+    // must be Frame or Dialog
+    private Component requestComponent;
+
+    // input context that is requesting input method switch
+    private InputContext requestInputContext;
+
+    // IM preference stuff
+    private static final String preferredIMNode = "/sun/awt/im/preferredInputMethod";
+    private static final String descriptorKey = "descriptor";
+    private Hashtable<String, InputMethodLocator> preferredLocatorCache = new Hashtable<>();
+    private Preferences userRoot;
+
+    ExecutableInputMethodManager() {
+
+        // set up host adapter locator
+        Toolkit toolkit = Toolkit.getDefaultToolkit();
+        try {
+            if (toolkit instanceof InputMethodSupport) {
+                InputMethodDescriptor hostAdapterDescriptor =
+                    ((InputMethodSupport)toolkit)
+                    .getInputMethodAdapterDescriptor();
+                if (hostAdapterDescriptor != null) {
+                    hostAdapterLocator = new InputMethodLocator(hostAdapterDescriptor, null, null);
+                }
+            }
+        } catch (AWTException e) {
+            // if we can't get a descriptor, we'll just have to do without native input methods
+        }
+
+        javaInputMethodLocatorList = new Vector<InputMethodLocator>();
+        initializeInputMethodLocatorList();
+    }
+
+    synchronized void initialize() {
+        selectInputMethodMenuTitle = Toolkit.getProperty("AWT.InputMethodSelectionMenu", "Select Input Method");
+
+        triggerMenuString = selectInputMethodMenuTitle;
+    }
+
+    public void run() {
+        // If there are no multiple input methods to choose from, wait forever
+        while (!hasMultipleInputMethods()) {
+            try {
+                synchronized (this) {
+                    wait();
+                }
+            } catch (InterruptedException e) {
+            }
+        }
+
+        // Loop for processing input method change requests
+        while (true) {
+            waitForChangeRequest();
+            initializeInputMethodLocatorList();
+            try {
+                if (requestComponent != null) {
+                    showInputMethodMenuOnRequesterEDT(requestComponent);
+                } else {
+                    // show the popup menu within the event thread
+                    EventQueue.invokeAndWait(new Runnable() {
+                        public void run() {
+                            showInputMethodMenu();
+                        }
+                    });
+                }
+            } catch (InterruptedException ie) {
+            } catch (InvocationTargetException ite) {
+                // should we do anything under these exceptions?
+            }
+        }
+    }
+
+    // Shows Input Method Menu on the EDT of requester component
+    // to avoid side effects. See 6544309.
+    private void showInputMethodMenuOnRequesterEDT(Component requester)
+        throws InterruptedException, InvocationTargetException {
+
+        if (requester == null){
+            return;
+        }
+
+        class AWTInvocationLock {}
+        Object lock = new AWTInvocationLock();
+
+        InvocationEvent event =
+                new InvocationEvent(requester,
+                                    new Runnable() {
+                                        public void run() {
+                                            showInputMethodMenu();
+                                        }
+                                    },
+                                    lock,
+                                    true);
+
+        AppContext requesterAppContext = SunToolkit.targetToAppContext(requester);
+        synchronized (lock) {
+            SunToolkit.postEvent(requesterAppContext, event);
+            while (!event.isDispatched()) {
+                lock.wait();
+            }
+        }
+
+        Throwable eventThrowable = event.getThrowable();
+        if (eventThrowable != null) {
+            throw new InvocationTargetException(eventThrowable);
+        }
+    }
+
+    void setInputContext(InputContext inputContext) {
+        if (currentInputContext != null && inputContext != null) {
+            // don't throw this exception until 4237852 is fixed
+            // throw new IllegalStateException("Can't have two active InputContext at the same time");
+        }
+        currentInputContext = inputContext;
+    }
+
+    public synchronized void notifyChangeRequest(Component comp) {
+        if (!(comp instanceof Frame || comp instanceof Dialog))
+            return;
+
+        // if busy with the current request, ignore this request.
+        if (requestComponent != null)
+            return;
+
+        requestComponent = comp;
+        notify();
+    }
+
+    public synchronized void notifyChangeRequestByHotKey(Component comp) {
+        while (!(comp instanceof Frame || comp instanceof Dialog)) {
+            if (comp == null) {
+                // no Frame or Dialog found in containment hierarchy.
+                return;
+            }
+            comp = comp.getParent();
+        }
+
+        notifyChangeRequest(comp);
+    }
+
+    public String getTriggerMenuString() {
+        return triggerMenuString;
+    }
+
+    /*
+     * Returns true if the environment indicates there are multiple input methods
+     */
+    boolean hasMultipleInputMethods() {
+        return ((hostAdapterLocator != null) && (javaInputMethodCount > 0)
+                || (javaInputMethodCount > 1));
+    }
+
+    private synchronized void waitForChangeRequest() {
+        try {
+            while (requestComponent == null) {
+                wait();
+            }
+        } catch (InterruptedException e) {
+        }
+    }
+
+    /*
+     * initializes the input method locator list for all
+     * installed input method descriptors.
+     */
+    private void initializeInputMethodLocatorList() {
+        synchronized (javaInputMethodLocatorList) {
+            javaInputMethodLocatorList.clear();
+            try {
+                AccessController.doPrivileged(new PrivilegedExceptionAction<Object>() {
+                    public Object run() {
+                        for (InputMethodDescriptor descriptor :
+                            ServiceLoader.loadInstalled(InputMethodDescriptor.class)) {
+                            ClassLoader cl = descriptor.getClass().getClassLoader();
+                            javaInputMethodLocatorList.add(new InputMethodLocator(descriptor, cl, null));
+                        }
+                        return null;
+                    }
+                });
+            }  catch (PrivilegedActionException e) {
+                e.printStackTrace();
+            }
+            javaInputMethodCount = javaInputMethodLocatorList.size();
+        }
+
+        if (hasMultipleInputMethods()) {
+            // initialize preferences
+            if (userRoot == null) {
+                userRoot = getUserRoot();
+            }
+        } else {
+            // indicate to clients not to offer the menu
+            triggerMenuString = null;
+        }
+    }
+
+    private void showInputMethodMenu() {
+
+        if (!hasMultipleInputMethods()) {
+            requestComponent = null;
+            return;
+        }
+
+        // initialize pop-up menu
+        selectionMenu = InputMethodPopupMenu.getInstance(requestComponent, selectInputMethodMenuTitle);
+
+        // we have to rebuild the menu each time because
+        // some input methods (such as IIIMP) may change
+        // their list of supported locales dynamically
+        selectionMenu.removeAll();
+
+        // get information about the currently selected input method
+        // ??? if there's no current input context, what's the point
+        // of showing the menu?
+        String currentSelection = getCurrentSelection();
+
+        // Add menu item for host adapter
+        if (hostAdapterLocator != null) {
+            selectionMenu.addOneInputMethodToMenu(hostAdapterLocator, currentSelection);
+            selectionMenu.addSeparator();
+        }
+
+        // Add menu items for other input methods
+        for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
+            InputMethodLocator locator = javaInputMethodLocatorList.get(i);
+            selectionMenu.addOneInputMethodToMenu(locator, currentSelection);
+        }
+
+        synchronized (this) {
+            selectionMenu.addToComponent(requestComponent);
+            requestInputContext = currentInputContext;
+            selectionMenu.show(requestComponent, 60, 80); // TODO: get proper x, y...
+            requestComponent = null;
+        }
+    }
+
+    private String getCurrentSelection() {
+        InputContext inputContext = currentInputContext;
+        if (inputContext != null) {
+            InputMethodLocator locator = inputContext.getInputMethodLocator();
+            if (locator != null) {
+                return locator.getActionCommandString();
+            }
+        }
+        return null;
+    }
+
+    synchronized void changeInputMethod(String choice) {
+        InputMethodLocator locator = null;
+
+        String inputMethodName = choice;
+        String localeString = null;
+        int index = choice.indexOf('\n');
+        if (index != -1) {
+            localeString = choice.substring(index + 1);
+            inputMethodName = choice.substring(0, index);
+        }
+        if (hostAdapterLocator.getActionCommandString().equals(inputMethodName)) {
+            locator = hostAdapterLocator;
+        } else {
+            for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
+                InputMethodLocator candidate = javaInputMethodLocatorList.get(i);
+                String name = candidate.getActionCommandString();
+                if (name.equals(inputMethodName)) {
+                    locator = candidate;
+                    break;
+                }
+            }
+        }
+
+        if (locator != null && localeString != null) {
+            String language = "", country = "", variant = "";
+            int postIndex = localeString.indexOf('_');
+            if (postIndex == -1) {
+                language = localeString;
+            } else {
+                language = localeString.substring(0, postIndex);
+                int preIndex = postIndex + 1;
+                postIndex = localeString.indexOf('_', preIndex);
+                if (postIndex == -1) {
+                    country = localeString.substring(preIndex);
+                } else {
+                    country = localeString.substring(preIndex, postIndex);
+                    variant = localeString.substring(postIndex + 1);
+                }
+            }
+            Locale locale = new Locale(language, country, variant);
+            locator = locator.deriveLocator(locale);
+        }
+
+        if (locator == null)
+            return;
+
+        // tell the input context about the change
+        if (requestInputContext != null) {
+            requestInputContext.changeInputMethod(locator);
+            requestInputContext = null;
+
+            // remember the selection
+            putPreferredInputMethod(locator);
+        }
+    }
+
+    InputMethodLocator findInputMethod(Locale locale) {
+        // look for preferred input method first
+        InputMethodLocator locator = getPreferredInputMethod(locale);
+        if (locator != null) {
+            return locator;
+        }
+
+        if (hostAdapterLocator != null && hostAdapterLocator.isLocaleAvailable(locale)) {
+            return hostAdapterLocator.deriveLocator(locale);
+        }
+
+        // Update the locator list
+        initializeInputMethodLocatorList();
+
+        for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
+            InputMethodLocator candidate = javaInputMethodLocatorList.get(i);
+            if (candidate.isLocaleAvailable(locale)) {
+                return candidate.deriveLocator(locale);
+            }
+        }
+        return null;
+    }
+
+    Locale getDefaultKeyboardLocale() {
+        Toolkit toolkit = Toolkit.getDefaultToolkit();
+        if (toolkit instanceof InputMethodSupport) {
+            return ((InputMethodSupport)toolkit).getDefaultKeyboardLocale();
+        } else {
+            return Locale.getDefault();
+        }
+    }
+
+    /**
+     * Returns a InputMethodLocator object that the
+     * user prefers for the given locale.
+     *
+     * @param locale Locale for which the user prefers the input method.
+     */
+    private synchronized InputMethodLocator getPreferredInputMethod(Locale locale) {
+        InputMethodLocator preferredLocator = null;
+
+        if (!hasMultipleInputMethods()) {
+            // No need to look for a preferred Java input method
+            return null;
+        }
+
+        // look for the cached preference first.
+        preferredLocator = preferredLocatorCache.get(locale.toString().intern());
+        if (preferredLocator != null) {
+            return preferredLocator;
+        }
+
+        // look for the preference in the user preference tree
+        String nodePath = findPreferredInputMethodNode(locale);
+        String descriptorName = readPreferredInputMethod(nodePath);
+        Locale advertised;
+
+        // get the locator object
+        if (descriptorName != null) {
+            // check for the host adapter first
+            if (hostAdapterLocator != null &&
+                hostAdapterLocator.getDescriptor().getClass().getName().equals(descriptorName)) {
+                advertised = getAdvertisedLocale(hostAdapterLocator, locale);
+                if (advertised != null) {
+                    preferredLocator = hostAdapterLocator.deriveLocator(advertised);
+                    preferredLocatorCache.put(locale.toString().intern(), preferredLocator);
+                }
+                return preferredLocator;
+            }
+            // look for Java input methods
+            for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
+                InputMethodLocator locator = javaInputMethodLocatorList.get(i);
+                InputMethodDescriptor descriptor = locator.getDescriptor();
+                if (descriptor.getClass().getName().equals(descriptorName)) {
+                    advertised = getAdvertisedLocale(locator, locale);
+                    if (advertised != null) {
+                        preferredLocator = locator.deriveLocator(advertised);
+                        preferredLocatorCache.put(locale.toString().intern(), preferredLocator);
+                    }
+                    return preferredLocator;
+                }
+            }
+
+            // maybe preferred input method information is bogus.
+            writePreferredInputMethod(nodePath, null);
+        }
+
+        return null;
+    }
+
+    private String findPreferredInputMethodNode(Locale locale) {
+        if (userRoot == null) {
+            return null;
+        }
+
+        // create locale node relative path
+        String nodePath = preferredIMNode + "/" + createLocalePath(locale);
+
+        // look for the descriptor
+        while (!nodePath.equals(preferredIMNode)) {
+            try {
+                if (userRoot.nodeExists(nodePath)) {
+                    if (readPreferredInputMethod(nodePath) != null) {
+                        return nodePath;
+                    }
+                }
+            } catch (BackingStoreException bse) {
+            }
+
+            // search at parent's node
+            nodePath = nodePath.substring(0, nodePath.lastIndexOf('/'));
+        }
+
+        return null;
+    }
+
+    private String readPreferredInputMethod(String nodePath) {
+        if ((userRoot == null) || (nodePath == null)) {
+            return null;
+        }
+
+        return userRoot.node(nodePath).get(descriptorKey, null);
+    }
+
+    /**
+     * Writes the preferred input method descriptor class name into
+     * the user's Preferences tree in accordance with the given locale.
+     *
+     * @param inputMethodLocator input method locator to remember.
+     */
+    private synchronized void putPreferredInputMethod(InputMethodLocator locator) {
+        InputMethodDescriptor descriptor = locator.getDescriptor();
+        Locale preferredLocale = locator.getLocale();
+
+        if (preferredLocale == null) {
+            // check available locales of the input method
+            try {
+                Locale[] availableLocales = descriptor.getAvailableLocales();
+                if (availableLocales.length == 1) {
+                    preferredLocale = availableLocales[0];
+                } else {
+                    // there is no way to know which locale is the preferred one, so do nothing.
+                    return;
+                }
+            } catch (AWTException ae) {
+                // do nothing here, either.
+                return;
+            }
+        }
+
+        // for regions that have only one language, we need to regard
+        // "xx_YY" as "xx" when putting the preference into tree
+        if (preferredLocale.equals(Locale.JAPAN)) {
+            preferredLocale = Locale.JAPANESE;
+        }
+        if (preferredLocale.equals(Locale.KOREA)) {
+            preferredLocale = Locale.KOREAN;
+        }
+        if (preferredLocale.equals(new Locale("th", "TH"))) {
+            preferredLocale = new Locale("th");
+        }
+
+        // obtain node
+        String path = preferredIMNode + "/" + createLocalePath(preferredLocale);
+
+        // write in the preference tree
+        writePreferredInputMethod(path, descriptor.getClass().getName());
+        preferredLocatorCache.put(preferredLocale.toString().intern(),
+            locator.deriveLocator(preferredLocale));
+
+        return;
+    }
+
+    private String createLocalePath(Locale locale) {
+        String language = locale.getLanguage();
+        String country = locale.getCountry();
+        String variant = locale.getVariant();
+        String localePath = null;
+        if (!variant.equals("")) {
+            localePath = "_" + language + "/_" + country + "/_" + variant;
+        } else if (!country.equals("")) {
+            localePath = "_" + language + "/_" + country;
+        } else {
+            localePath = "_" + language;
+        }
+
+        return localePath;
+    }
+
+    private void writePreferredInputMethod(String path, String descriptorName) {
+        if (userRoot != null) {
+            Preferences node = userRoot.node(path);
+
+            // record it
+            if (descriptorName != null) {
+                node.put(descriptorKey, descriptorName);
+            } else {
+                node.remove(descriptorKey);
+            }
+        }
+    }
+
+    private Preferences getUserRoot() {
+        return AccessController.doPrivileged(new PrivilegedAction<Preferences>() {
+            public Preferences run() {
+                return Preferences.userRoot();
+            }
+        });
+    }
+
+    private Locale getAdvertisedLocale(InputMethodLocator locator, Locale locale) {
+        Locale advertised = null;
+
+        if (locator.isLocaleAvailable(locale)) {
+            advertised = locale;
+        } else if (locale.getLanguage().equals("ja")) {
+            // for Japanese, Korean, and Thai, check whether the input method supports
+            // language or language_COUNTRY.
+            if (locator.isLocaleAvailable(Locale.JAPAN)) {
+                advertised = Locale.JAPAN;
+            } else if (locator.isLocaleAvailable(Locale.JAPANESE)) {
+                advertised = Locale.JAPANESE;
+            }
+        } else if (locale.getLanguage().equals("ko")) {
+            if (locator.isLocaleAvailable(Locale.KOREA)) {
+                advertised = Locale.KOREA;
+            } else if (locator.isLocaleAvailable(Locale.KOREAN)) {
+                advertised = Locale.KOREAN;
+            }
+        } else if (locale.getLanguage().equals("th")) {
+            if (locator.isLocaleAvailable(new Locale("th", "TH"))) {
+                advertised = new Locale("th", "TH");
+            } else if (locator.isLocaleAvailable(new Locale("th"))) {
+                advertised = new Locale("th");
+            }
+        }
+
+        return advertised;
+    }
+}
--- a/src/share/classes/sun/awt/im/InputMethodManager.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/awt/im/InputMethodManager.java	Mon Nov 05 10:33:18 2012 -0500
@@ -229,578 +229,3 @@
     abstract boolean hasMultipleInputMethods();
 
 }
-
-/**
- * <code>ExecutableInputMethodManager</code> is the implementation of the
- * <code>InputMethodManager</code> class. It is runnable as a separate
- * thread in the AWT environment.&nbsp;
- * <code>InputMethodManager.getInstance()</code> creates an instance of
- * <code>ExecutableInputMethodManager</code> and executes it as a deamon
- * thread.
- *
- * @see InputMethodManager
- */
-class ExecutableInputMethodManager extends InputMethodManager
-                                   implements Runnable
-{
-    // the input context that's informed about selections from the user interface
-    private InputContext currentInputContext;
-
-    // Menu item string for the trigger menu.
-    private String triggerMenuString;
-
-    // popup menu for selecting an input method
-    private InputMethodPopupMenu selectionMenu;
-    private static String selectInputMethodMenuTitle;
-
-    // locator and name of host adapter
-    private InputMethodLocator hostAdapterLocator;
-
-    // locators for Java input methods
-    private int javaInputMethodCount;         // number of Java input methods found
-    private Vector<InputMethodLocator> javaInputMethodLocatorList;
-
-    // component that is requesting input method switch
-    // must be Frame or Dialog
-    private Component requestComponent;
-
-    // input context that is requesting input method switch
-    private InputContext requestInputContext;
-
-    // IM preference stuff
-    private static final String preferredIMNode = "/sun/awt/im/preferredInputMethod";
-    private static final String descriptorKey = "descriptor";
-    private Hashtable<String, InputMethodLocator> preferredLocatorCache = new Hashtable<>();
-    private Preferences userRoot;
-
-    ExecutableInputMethodManager() {
-
-        // set up host adapter locator
-        Toolkit toolkit = Toolkit.getDefaultToolkit();
-        try {
-            if (toolkit instanceof InputMethodSupport) {
-                InputMethodDescriptor hostAdapterDescriptor =
-                    ((InputMethodSupport)toolkit)
-                    .getInputMethodAdapterDescriptor();
-                if (hostAdapterDescriptor != null) {
-                    hostAdapterLocator = new InputMethodLocator(hostAdapterDescriptor, null, null);
-                }
-            }
-        } catch (AWTException e) {
-            // if we can't get a descriptor, we'll just have to do without native input methods
-        }
-
-        javaInputMethodLocatorList = new Vector<InputMethodLocator>();
-        initializeInputMethodLocatorList();
-    }
-
-    synchronized void initialize() {
-        selectInputMethodMenuTitle = Toolkit.getProperty("AWT.InputMethodSelectionMenu", "Select Input Method");
-
-        triggerMenuString = selectInputMethodMenuTitle;
-    }
-
-    public void run() {
-        // If there are no multiple input methods to choose from, wait forever
-        while (!hasMultipleInputMethods()) {
-            try {
-                synchronized (this) {
-                    wait();
-                }
-            } catch (InterruptedException e) {
-            }
-        }
-
-        // Loop for processing input method change requests
-        while (true) {
-            waitForChangeRequest();
-            initializeInputMethodLocatorList();
-            try {
-                if (requestComponent != null) {
-                    showInputMethodMenuOnRequesterEDT(requestComponent);
-                } else {
-                    // show the popup menu within the event thread
-                    EventQueue.invokeAndWait(new Runnable() {
-                        public void run() {
-                            showInputMethodMenu();
-                        }
-                    });
-                }
-            } catch (InterruptedException ie) {
-            } catch (InvocationTargetException ite) {
-                // should we do anything under these exceptions?
-            }
-        }
-    }
-
-    // Shows Input Method Menu on the EDT of requester component
-    // to avoid side effects. See 6544309.
-    private void showInputMethodMenuOnRequesterEDT(Component requester)
-        throws InterruptedException, InvocationTargetException {
-
-        if (requester == null){
-            return;
-        }
-
-        class AWTInvocationLock {}
-        Object lock = new AWTInvocationLock();
-
-        InvocationEvent event =
-                new InvocationEvent(requester,
-                                    new Runnable() {
-                                        public void run() {
-                                            showInputMethodMenu();
-                                        }
-                                    },
-                                    lock,
-                                    true);
-
-        AppContext requesterAppContext = SunToolkit.targetToAppContext(requester);
-        synchronized (lock) {
-            SunToolkit.postEvent(requesterAppContext, event);
-            while (!event.isDispatched()) {
-                lock.wait();
-            }
-        }
-
-        Throwable eventThrowable = event.getThrowable();
-        if (eventThrowable != null) {
-            throw new InvocationTargetException(eventThrowable);
-        }
-    }
-
-    void setInputContext(InputContext inputContext) {
-        if (currentInputContext != null && inputContext != null) {
-            // don't throw this exception until 4237852 is fixed
-            // throw new IllegalStateException("Can't have two active InputContext at the same time");
-        }
-        currentInputContext = inputContext;
-    }
-
-    public synchronized void notifyChangeRequest(Component comp) {
-        if (!(comp instanceof Frame || comp instanceof Dialog))
-            return;
-
-        // if busy with the current request, ignore this request.
-        if (requestComponent != null)
-            return;
-
-        requestComponent = comp;
-        notify();
-    }
-
-    public synchronized void notifyChangeRequestByHotKey(Component comp) {
-        while (!(comp instanceof Frame || comp instanceof Dialog)) {
-            if (comp == null) {
-                // no Frame or Dialog found in containment hierarchy.
-                return;
-            }
-            comp = comp.getParent();
-        }
-
-        notifyChangeRequest(comp);
-    }
-
-    public String getTriggerMenuString() {
-        return triggerMenuString;
-    }
-
-    /*
-     * Returns true if the environment indicates there are multiple input methods
-     */
-    boolean hasMultipleInputMethods() {
-        return ((hostAdapterLocator != null) && (javaInputMethodCount > 0)
-                || (javaInputMethodCount > 1));
-    }
-
-    private synchronized void waitForChangeRequest() {
-        try {
-            while (requestComponent == null) {
-                wait();
-            }
-        } catch (InterruptedException e) {
-        }
-    }
-
-    /*
-     * initializes the input method locator list for all
-     * installed input method descriptors.
-     */
-    private void initializeInputMethodLocatorList() {
-        synchronized (javaInputMethodLocatorList) {
-            javaInputMethodLocatorList.clear();
-            try {
-                AccessController.doPrivileged(new PrivilegedExceptionAction<Object>() {
-                    public Object run() {
-                        for (InputMethodDescriptor descriptor :
-                            ServiceLoader.loadInstalled(InputMethodDescriptor.class)) {
-                            ClassLoader cl = descriptor.getClass().getClassLoader();
-                            javaInputMethodLocatorList.add(new InputMethodLocator(descriptor, cl, null));
-                        }
-                        return null;
-                    }
-                });
-            }  catch (PrivilegedActionException e) {
-                e.printStackTrace();
-            }
-            javaInputMethodCount = javaInputMethodLocatorList.size();
-        }
-
-        if (hasMultipleInputMethods()) {
-            // initialize preferences
-            if (userRoot == null) {
-                userRoot = getUserRoot();
-            }
-        } else {
-            // indicate to clients not to offer the menu
-            triggerMenuString = null;
-        }
-    }
-
-    private void showInputMethodMenu() {
-
-        if (!hasMultipleInputMethods()) {
-            requestComponent = null;
-            return;
-        }
-
-        // initialize pop-up menu
-        selectionMenu = InputMethodPopupMenu.getInstance(requestComponent, selectInputMethodMenuTitle);
-
-        // we have to rebuild the menu each time because
-        // some input methods (such as IIIMP) may change
-        // their list of supported locales dynamically
-        selectionMenu.removeAll();
-
-        // get information about the currently selected input method
-        // ??? if there's no current input context, what's the point
-        // of showing the menu?
-        String currentSelection = getCurrentSelection();
-
-        // Add menu item for host adapter
-        if (hostAdapterLocator != null) {
-            selectionMenu.addOneInputMethodToMenu(hostAdapterLocator, currentSelection);
-            selectionMenu.addSeparator();
-        }
-
-        // Add menu items for other input methods
-        for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
-            InputMethodLocator locator = javaInputMethodLocatorList.get(i);
-            selectionMenu.addOneInputMethodToMenu(locator, currentSelection);
-        }
-
-        synchronized (this) {
-            selectionMenu.addToComponent(requestComponent);
-            requestInputContext = currentInputContext;
-            selectionMenu.show(requestComponent, 60, 80); // TODO: get proper x, y...
-            requestComponent = null;
-        }
-    }
-
-    private String getCurrentSelection() {
-        InputContext inputContext = currentInputContext;
-        if (inputContext != null) {
-            InputMethodLocator locator = inputContext.getInputMethodLocator();
-            if (locator != null) {
-                return locator.getActionCommandString();
-            }
-        }
-        return null;
-    }
-
-    synchronized void changeInputMethod(String choice) {
-        InputMethodLocator locator = null;
-
-        String inputMethodName = choice;
-        String localeString = null;
-        int index = choice.indexOf('\n');
-        if (index != -1) {
-            localeString = choice.substring(index + 1);
-            inputMethodName = choice.substring(0, index);
-        }
-        if (hostAdapterLocator.getActionCommandString().equals(inputMethodName)) {
-            locator = hostAdapterLocator;
-        } else {
-            for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
-                InputMethodLocator candidate = javaInputMethodLocatorList.get(i);
-                String name = candidate.getActionCommandString();
-                if (name.equals(inputMethodName)) {
-                    locator = candidate;
-                    break;
-                }
-            }
-        }
-
-        if (locator != null && localeString != null) {
-            String language = "", country = "", variant = "";
-            int postIndex = localeString.indexOf('_');
-            if (postIndex == -1) {
-                language = localeString;
-            } else {
-                language = localeString.substring(0, postIndex);
-                int preIndex = postIndex + 1;
-                postIndex = localeString.indexOf('_', preIndex);
-                if (postIndex == -1) {
-                    country = localeString.substring(preIndex);
-                } else {
-                    country = localeString.substring(preIndex, postIndex);
-                    variant = localeString.substring(postIndex + 1);
-                }
-            }
-            Locale locale = new Locale(language, country, variant);
-            locator = locator.deriveLocator(locale);
-        }
-
-        if (locator == null)
-            return;
-
-        // tell the input context about the change
-        if (requestInputContext != null) {
-            requestInputContext.changeInputMethod(locator);
-            requestInputContext = null;
-
-            // remember the selection
-            putPreferredInputMethod(locator);
-        }
-    }
-
-    InputMethodLocator findInputMethod(Locale locale) {
-        // look for preferred input method first
-        InputMethodLocator locator = getPreferredInputMethod(locale);
-        if (locator != null) {
-            return locator;
-        }
-
-        if (hostAdapterLocator != null && hostAdapterLocator.isLocaleAvailable(locale)) {
-            return hostAdapterLocator.deriveLocator(locale);
-        }
-
-        // Update the locator list
-        initializeInputMethodLocatorList();
-
-        for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
-            InputMethodLocator candidate = javaInputMethodLocatorList.get(i);
-            if (candidate.isLocaleAvailable(locale)) {
-                return candidate.deriveLocator(locale);
-            }
-        }
-        return null;
-    }
-
-    Locale getDefaultKeyboardLocale() {
-        Toolkit toolkit = Toolkit.getDefaultToolkit();
-        if (toolkit instanceof InputMethodSupport) {
-            return ((InputMethodSupport)toolkit).getDefaultKeyboardLocale();
-        } else {
-            return Locale.getDefault();
-        }
-    }
-
-    /**
-     * Returns a InputMethodLocator object that the
-     * user prefers for the given locale.
-     *
-     * @param locale Locale for which the user prefers the input method.
-     */
-    private synchronized InputMethodLocator getPreferredInputMethod(Locale locale) {
-        InputMethodLocator preferredLocator = null;
-
-        if (!hasMultipleInputMethods()) {
-            // No need to look for a preferred Java input method
-            return null;
-        }
-
-        // look for the cached preference first.
-        preferredLocator = preferredLocatorCache.get(locale.toString().intern());
-        if (preferredLocator != null) {
-            return preferredLocator;
-        }
-
-        // look for the preference in the user preference tree
-        String nodePath = findPreferredInputMethodNode(locale);
-        String descriptorName = readPreferredInputMethod(nodePath);
-        Locale advertised;
-
-        // get the locator object
-        if (descriptorName != null) {
-            // check for the host adapter first
-            if (hostAdapterLocator != null &&
-                hostAdapterLocator.getDescriptor().getClass().getName().equals(descriptorName)) {
-                advertised = getAdvertisedLocale(hostAdapterLocator, locale);
-                if (advertised != null) {
-                    preferredLocator = hostAdapterLocator.deriveLocator(advertised);
-                    preferredLocatorCache.put(locale.toString().intern(), preferredLocator);
-                }
-                return preferredLocator;
-            }
-            // look for Java input methods
-            for (int i = 0; i < javaInputMethodLocatorList.size(); i++) {
-                InputMethodLocator locator = javaInputMethodLocatorList.get(i);
-                InputMethodDescriptor descriptor = locator.getDescriptor();
-                if (descriptor.getClass().getName().equals(descriptorName)) {
-                    advertised = getAdvertisedLocale(locator, locale);
-                    if (advertised != null) {
-                        preferredLocator = locator.deriveLocator(advertised);
-                        preferredLocatorCache.put(locale.toString().intern(), preferredLocator);
-                    }
-                    return preferredLocator;
-                }
-            }
-
-            // maybe preferred input method information is bogus.
-            writePreferredInputMethod(nodePath, null);
-        }
-
-        return null;
-    }
-
-    private String findPreferredInputMethodNode(Locale locale) {
-        if (userRoot == null) {
-            return null;
-        }
-
-        // create locale node relative path
-        String nodePath = preferredIMNode + "/" + createLocalePath(locale);
-
-        // look for the descriptor
-        while (!nodePath.equals(preferredIMNode)) {
-            try {
-                if (userRoot.nodeExists(nodePath)) {
-                    if (readPreferredInputMethod(nodePath) != null) {
-                        return nodePath;
-                    }
-                }
-            } catch (BackingStoreException bse) {
-            }
-
-            // search at parent's node
-            nodePath = nodePath.substring(0, nodePath.lastIndexOf('/'));
-        }
-
-        return null;
-    }
-
-    private String readPreferredInputMethod(String nodePath) {
-        if ((userRoot == null) || (nodePath == null)) {
-            return null;
-        }
-
-        return userRoot.node(nodePath).get(descriptorKey, null);
-    }
-
-    /**
-     * Writes the preferred input method descriptor class name into
-     * the user's Preferences tree in accordance with the given locale.
-     *
-     * @param inputMethodLocator input method locator to remember.
-     */
-    private synchronized void putPreferredInputMethod(InputMethodLocator locator) {
-        InputMethodDescriptor descriptor = locator.getDescriptor();
-        Locale preferredLocale = locator.getLocale();
-
-        if (preferredLocale == null) {
-            // check available locales of the input method
-            try {
-                Locale[] availableLocales = descriptor.getAvailableLocales();
-                if (availableLocales.length == 1) {
-                    preferredLocale = availableLocales[0];
-                } else {
-                    // there is no way to know which locale is the preferred one, so do nothing.
-                    return;
-                }
-            } catch (AWTException ae) {
-                // do nothing here, either.
-                return;
-            }
-        }
-
-        // for regions that have only one language, we need to regard
-        // "xx_YY" as "xx" when putting the preference into tree
-        if (preferredLocale.equals(Locale.JAPAN)) {
-            preferredLocale = Locale.JAPANESE;
-        }
-        if (preferredLocale.equals(Locale.KOREA)) {
-            preferredLocale = Locale.KOREAN;
-        }
-        if (preferredLocale.equals(new Locale("th", "TH"))) {
-            preferredLocale = new Locale("th");
-        }
-
-        // obtain node
-        String path = preferredIMNode + "/" + createLocalePath(preferredLocale);
-
-        // write in the preference tree
-        writePreferredInputMethod(path, descriptor.getClass().getName());
-        preferredLocatorCache.put(preferredLocale.toString().intern(),
-            locator.deriveLocator(preferredLocale));
-
-        return;
-    }
-
-    private String createLocalePath(Locale locale) {
-        String language = locale.getLanguage();
-        String country = locale.getCountry();
-        String variant = locale.getVariant();
-        String localePath = null;
-        if (!variant.equals("")) {
-            localePath = "_" + language + "/_" + country + "/_" + variant;
-        } else if (!country.equals("")) {
-            localePath = "_" + language + "/_" + country;
-        } else {
-            localePath = "_" + language;
-        }
-
-        return localePath;
-    }
-
-    private void writePreferredInputMethod(String path, String descriptorName) {
-        if (userRoot != null) {
-            Preferences node = userRoot.node(path);
-
-            // record it
-            if (descriptorName != null) {
-                node.put(descriptorKey, descriptorName);
-            } else {
-                node.remove(descriptorKey);
-            }
-        }
-    }
-
-    private Preferences getUserRoot() {
-        return AccessController.doPrivileged(new PrivilegedAction<Preferences>() {
-            public Preferences run() {
-                return Preferences.userRoot();
-            }
-        });
-    }
-
-    private Locale getAdvertisedLocale(InputMethodLocator locator, Locale locale) {
-        Locale advertised = null;
-
-        if (locator.isLocaleAvailable(locale)) {
-            advertised = locale;
-        } else if (locale.getLanguage().equals("ja")) {
-            // for Japanese, Korean, and Thai, check whether the input method supports
-            // language or language_COUNTRY.
-            if (locator.isLocaleAvailable(Locale.JAPAN)) {
-                advertised = Locale.JAPAN;
-            } else if (locator.isLocaleAvailable(Locale.JAPANESE)) {
-                advertised = Locale.JAPANESE;
-            }
-        } else if (locale.getLanguage().equals("ko")) {
-            if (locator.isLocaleAvailable(Locale.KOREA)) {
-                advertised = Locale.KOREA;
-            } else if (locator.isLocaleAvailable(Locale.KOREAN)) {
-                advertised = Locale.KOREAN;
-            }
-        } else if (locale.getLanguage().equals("th")) {
-            if (locator.isLocaleAvailable(new Locale("th", "TH"))) {
-                advertised = new Locale("th", "TH");
-            } else if (locator.isLocaleAvailable(new Locale("th"))) {
-                advertised = new Locale("th");
-            }
-        }
-
-        return advertised;
-    }
-}
--- a/src/share/classes/sun/invoke/anon/AnonymousClassLoader.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/invoke/anon/AnonymousClassLoader.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2012, 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
@@ -73,74 +73,14 @@
 public class AnonymousClassLoader {
     final Class<?> hostClass;
 
-    // Note: Do not refactor the calls to checkHostClass unless you
-    //       also adjust this constant:
-    private static int CHC_CALLERS = 3;
-
-    public AnonymousClassLoader() {
-        this.hostClass = checkHostClass(null);
-    }
-    public AnonymousClassLoader(Class<?> hostClass) {
-        this.hostClass = checkHostClass(hostClass);
-    }
-
-    private static Class<?> getTopLevelClass(Class<?> clazz) {
-      for(Class<?> outer = clazz.getDeclaringClass(); outer != null;
-          outer = outer.getDeclaringClass()) {
-        clazz = outer;
-      }
-      return clazz;
+    // Privileged constructor.
+    private AnonymousClassLoader(Class<?> hostClass) {
+        this.hostClass = hostClass;
     }
 
-    private static Class<?> checkHostClass(Class<?> hostClass) {
-        // called only from the constructor
-        // does a context-sensitive check on caller class
-        // CC[0..3] = {Reflection, this.checkHostClass, this.<init>, caller}
-        Class<?> caller = sun.reflect.Reflection.getCallerClass(CHC_CALLERS);
-
-        if (caller == null) {
-            // called from the JVM directly
-            if (hostClass == null)
-                return AnonymousClassLoader.class; // anything central will do
-            return hostClass;
-        }
-
-        if (hostClass == null)
-            hostClass = caller; // default value is caller itself
-
-        // anonymous class will access hostClass on behalf of caller
-        Class<?> callee = hostClass;
-
-        if (caller == callee)
-            // caller can always nominate itself to grant caller's own access rights
-            return hostClass;
-
-        // normalize caller and callee to their top-level classes:
-        caller = getTopLevelClass(caller);
-        callee = getTopLevelClass(callee);
-        if (caller == callee)
-            return caller;
-
-        ClassLoader callerCL = caller.getClassLoader();
-        if (callerCL == null) {
-            // caller is trusted code, so accept the proposed hostClass
-            return hostClass;
-        }
-
-        // %%% should do something with doPrivileged, because trusted
-        // code should have a way to execute on behalf of
-        // partially-trusted clients
-
-        // Does the caller have the right to access the private
-        // members of the callee?  If not, raise an error.
-        final int ACC_PRIVATE = 2;
-        try {
-            sun.reflect.Reflection.ensureMemberAccess(caller, callee, null, ACC_PRIVATE);
-        } catch (IllegalAccessException ee) {
-            throw new IllegalArgumentException(ee);
-        }
-
-        return hostClass;
+    public static AnonymousClassLoader make(sun.misc.Unsafe unsafe, Class<?> hostClass) {
+        if (unsafe == null)  throw new NullPointerException();
+        return new AnonymousClassLoader(hostClass);
     }
 
     public Class<?> loadClass(byte[] classFile) {
@@ -249,7 +189,7 @@
     private static int fakeNameCounter = 99999;
 
     // ignore two warnings on this line:
-    static sun.misc.Unsafe unsafe = sun.misc.Unsafe.getUnsafe();
+    private static sun.misc.Unsafe unsafe = sun.misc.Unsafe.getUnsafe();
     // preceding line requires that this class be on the boot class path
 
     static private final Method defineAnonymousClass;
--- a/src/share/classes/sun/invoke/util/ValueConversions.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/invoke/util/ValueConversions.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2008, 2012, 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
@@ -475,7 +475,7 @@
                     .findStatic(THIS_CLASS, "fillNewTypedArray",
                           MethodType.methodType(Object[].class, Object[].class, Integer.class, Object[].class));
         } catch (NoSuchMethodException | IllegalAccessException ex) {
-            throw new InternalError("uncaught exception", ex);
+            throw newInternalError("uncaught exception", ex);
         }
     }
 
@@ -489,7 +489,7 @@
                 COPY_AS_PRIMITIVE_ARRAY = IMPL_LOOKUP.findStatic(THIS_CLASS, "copyAsPrimitiveArray", MethodType.methodType(Object.class, Wrapper.class, Object[].class));
                 MAKE_LIST = IMPL_LOOKUP.findStatic(THIS_CLASS, "makeList", MethodType.methodType(List.class, Object[].class));
             } catch (ReflectiveOperationException ex) {
-                throw new InternalError("uncaught exception", ex);
+                throw newInternalError("uncaught exception", ex);
             }
         }
     }
@@ -522,14 +522,19 @@
     static {
         MethodHandle mh = null;
         try {
-            java.lang.reflect.Method m = MethodHandles.class
+            final java.lang.reflect.Method m = MethodHandles.class
                 .getDeclaredMethod("collectArguments",
                     MethodHandle.class, int.class, MethodHandle.class);
-            m.setAccessible(true);
+            AccessController.doPrivileged(new PrivilegedAction<Void>() {
+                    @Override
+                    public Void run() {
+                        m.setAccessible(true);
+                        return null;
+                    }
+                });
             mh = IMPL_LOOKUP.unreflect(m);
-
-        } catch (ReflectiveOperationException | SecurityException ex) {
-            throw new InternalError(ex);
+        } catch (ReflectiveOperationException ex) {
+            throw newInternalError(ex);
         }
         COLLECT_ARGUMENTS = mh;
     }
@@ -1209,4 +1214,12 @@
     private static MethodHandle buildVarargsList(int nargs) {
         return MethodHandles.filterReturnValue(varargsArray(nargs), LazyStatics.MAKE_LIST);
     }
+
+    // handy shared exception makers (they simplify the common case code)
+    private static InternalError newInternalError(String message, Throwable cause) {
+        return new InternalError(message, cause);
+    }
+    private static InternalError newInternalError(Throwable cause) {
+        return new InternalError(cause);
+    }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/misc/FDBigInt.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,493 @@
+/*
+ * Copyright (c) 1996, 2011, 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.misc;
+
+/*
+ * A really, really simple bigint package
+ * tailored to the needs of floating base conversion.
+ */
+class FDBigInt {
+    int nWords; // number of words used
+    int data[]; // value: data[0] is least significant
+
+
+    public FDBigInt( int v ){
+        nWords = 1;
+        data = new int[1];
+        data[0] = v;
+    }
+
+    public FDBigInt( long v ){
+        data = new int[2];
+        data[0] = (int)v;
+        data[1] = (int)(v>>>32);
+        nWords = (data[1]==0) ? 1 : 2;
+    }
+
+    public FDBigInt( FDBigInt other ){
+        data = new int[nWords = other.nWords];
+        System.arraycopy( other.data, 0, data, 0, nWords );
+    }
+
+    private FDBigInt( int [] d, int n ){
+        data = d;
+        nWords = n;
+    }
+
+    public FDBigInt( long seed, char digit[], int nd0, int nd ){
+        int n= (nd+8)/9;        // estimate size needed.
+        if ( n < 2 ) n = 2;
+        data = new int[n];      // allocate enough space
+        data[0] = (int)seed;    // starting value
+        data[1] = (int)(seed>>>32);
+        nWords = (data[1]==0) ? 1 : 2;
+        int i = nd0;
+        int limit = nd-5;       // slurp digits 5 at a time.
+        int v;
+        while ( i < limit ){
+            int ilim = i+5;
+            v = (int)digit[i++]-(int)'0';
+            while( i <ilim ){
+                v = 10*v + (int)digit[i++]-(int)'0';
+            }
+            multaddMe( 100000, v); // ... where 100000 is 10^5.
+        }
+        int factor = 1;
+        v = 0;
+        while ( i < nd ){
+            v = 10*v + (int)digit[i++]-(int)'0';
+            factor *= 10;
+        }
+        if ( factor != 1 ){
+            multaddMe( factor, v );
+        }
+    }
+
+    /*
+     * Left shift by c bits.
+     * Shifts this in place.
+     */
+    public void
+    lshiftMe( int c )throws IllegalArgumentException {
+        if ( c <= 0 ){
+            if ( c == 0 )
+                return; // silly.
+            else
+                throw new IllegalArgumentException("negative shift count");
+        }
+        int wordcount = c>>5;
+        int bitcount  = c & 0x1f;
+        int anticount = 32-bitcount;
+        int t[] = data;
+        int s[] = data;
+        if ( nWords+wordcount+1 > t.length ){
+            // reallocate.
+            t = new int[ nWords+wordcount+1 ];
+        }
+        int target = nWords+wordcount;
+        int src    = nWords-1;
+        if ( bitcount == 0 ){
+            // special hack, since an anticount of 32 won't go!
+            System.arraycopy( s, 0, t, wordcount, nWords );
+            target = wordcount-1;
+        } else {
+            t[target--] = s[src]>>>anticount;
+            while ( src >= 1 ){
+                t[target--] = (s[src]<<bitcount) | (s[--src]>>>anticount);
+            }
+            t[target--] = s[src]<<bitcount;
+        }
+        while( target >= 0 ){
+            t[target--] = 0;
+        }
+        data = t;
+        nWords += wordcount + 1;
+        // may have constructed high-order word of 0.
+        // if so, trim it
+        while ( nWords > 1 && data[nWords-1] == 0 )
+            nWords--;
+    }
+
+    /*
+     * normalize this number by shifting until
+     * the MSB of the number is at 0x08000000.
+     * This is in preparation for quoRemIteration, below.
+     * The idea is that, to make division easier, we want the
+     * divisor to be "normalized" -- usually this means shifting
+     * the MSB into the high words sign bit. But because we know that
+     * the quotient will be 0 < q < 10, we would like to arrange that
+     * the dividend not span up into another word of precision.
+     * (This needs to be explained more clearly!)
+     */
+    public int
+    normalizeMe() throws IllegalArgumentException {
+        int src;
+        int wordcount = 0;
+        int bitcount  = 0;
+        int v = 0;
+        for ( src= nWords-1 ; src >= 0 && (v=data[src]) == 0 ; src--){
+            wordcount += 1;
+        }
+        if ( src < 0 ){
+            // oops. Value is zero. Cannot normalize it!
+            throw new IllegalArgumentException("zero value");
+        }
+        /*
+         * In most cases, we assume that wordcount is zero. This only
+         * makes sense, as we try not to maintain any high-order
+         * words full of zeros. In fact, if there are zeros, we will
+         * simply SHORTEN our number at this point. Watch closely...
+         */
+        nWords -= wordcount;
+        /*
+         * Compute how far left we have to shift v s.t. its highest-
+         * order bit is in the right place. Then call lshiftMe to
+         * do the work.
+         */
+        if ( (v & 0xf0000000) != 0 ){
+            // will have to shift up into the next word.
+            // too bad.
+            for( bitcount = 32 ; (v & 0xf0000000) != 0 ; bitcount-- )
+                v >>>= 1;
+        } else {
+            while ( v <= 0x000fffff ){
+                // hack: byte-at-a-time shifting
+                v <<= 8;
+                bitcount += 8;
+            }
+            while ( v <= 0x07ffffff ){
+                v <<= 1;
+                bitcount += 1;
+            }
+        }
+        if ( bitcount != 0 )
+            lshiftMe( bitcount );
+        return bitcount;
+    }
+
+    /*
+     * Multiply a FDBigInt by an int.
+     * Result is a new FDBigInt.
+     */
+    public FDBigInt
+    mult( int iv ) {
+        long v = iv;
+        int r[];
+        long p;
+
+        // guess adequate size of r.
+        r = new int[ ( v * ((long)data[nWords-1]&0xffffffffL) > 0xfffffffL ) ? nWords+1 : nWords ];
+        p = 0L;
+        for( int i=0; i < nWords; i++ ) {
+            p += v * ((long)data[i]&0xffffffffL);
+            r[i] = (int)p;
+            p >>>= 32;
+        }
+        if ( p == 0L){
+            return new FDBigInt( r, nWords );
+        } else {
+            r[nWords] = (int)p;
+            return new FDBigInt( r, nWords+1 );
+        }
+    }
+
+    /*
+     * Multiply a FDBigInt by an int and add another int.
+     * Result is computed in place.
+     * Hope it fits!
+     */
+    public void
+    multaddMe( int iv, int addend ) {
+        long v = iv;
+        long p;
+
+        // unroll 0th iteration, doing addition.
+        p = v * ((long)data[0]&0xffffffffL) + ((long)addend&0xffffffffL);
+        data[0] = (int)p;
+        p >>>= 32;
+        for( int i=1; i < nWords; i++ ) {
+            p += v * ((long)data[i]&0xffffffffL);
+            data[i] = (int)p;
+            p >>>= 32;
+        }
+        if ( p != 0L){
+            data[nWords] = (int)p; // will fail noisily if illegal!
+            nWords++;
+        }
+    }
+
+    /*
+     * Multiply a FDBigInt by another FDBigInt.
+     * Result is a new FDBigInt.
+     */
+    public FDBigInt
+    mult( FDBigInt other ){
+        // crudely guess adequate size for r
+        int r[] = new int[ nWords + other.nWords ];
+        int i;
+        // I think I am promised zeros...
+
+        for( i = 0; i < this.nWords; i++ ){
+            long v = (long)this.data[i] & 0xffffffffL; // UNSIGNED CONVERSION
+            long p = 0L;
+            int j;
+            for( j = 0; j < other.nWords; j++ ){
+                p += ((long)r[i+j]&0xffffffffL) + v*((long)other.data[j]&0xffffffffL); // UNSIGNED CONVERSIONS ALL 'ROUND.
+                r[i+j] = (int)p;
+                p >>>= 32;
+            }
+            r[i+j] = (int)p;
+        }
+        // compute how much of r we actually needed for all that.
+        for ( i = r.length-1; i> 0; i--)
+            if ( r[i] != 0 )
+                break;
+        return new FDBigInt( r, i+1 );
+    }
+
+    /*
+     * Add one FDBigInt to another. Return a FDBigInt
+     */
+    public FDBigInt
+    add( FDBigInt other ){
+        int i;
+        int a[], b[];
+        int n, m;
+        long c = 0L;
+        // arrange such that a.nWords >= b.nWords;
+        // n = a.nWords, m = b.nWords
+        if ( this.nWords >= other.nWords ){
+            a = this.data;
+            n = this.nWords;
+            b = other.data;
+            m = other.nWords;
+        } else {
+            a = other.data;
+            n = other.nWords;
+            b = this.data;
+            m = this.nWords;
+        }
+        int r[] = new int[ n ];
+        for ( i = 0; i < n; i++ ){
+            c += (long)a[i] & 0xffffffffL;
+            if ( i < m ){
+                c += (long)b[i] & 0xffffffffL;
+            }
+            r[i] = (int) c;
+            c >>= 32; // signed shift.
+        }
+        if ( c != 0L ){
+            // oops -- carry out -- need longer result.
+            int s[] = new int[ r.length+1 ];
+            System.arraycopy( r, 0, s, 0, r.length );
+            s[i++] = (int)c;
+            return new FDBigInt( s, i );
+        }
+        return new FDBigInt( r, i );
+    }
+
+    /*
+     * Subtract one FDBigInt from another. Return a FDBigInt
+     * Assert that the result is positive.
+     */
+    public FDBigInt
+    sub( FDBigInt other ){
+        int r[] = new int[ this.nWords ];
+        int i;
+        int n = this.nWords;
+        int m = other.nWords;
+        int nzeros = 0;
+        long c = 0L;
+        for ( i = 0; i < n; i++ ){
+            c += (long)this.data[i] & 0xffffffffL;
+            if ( i < m ){
+                c -= (long)other.data[i] & 0xffffffffL;
+            }
+            if ( ( r[i] = (int) c ) == 0 )
+                nzeros++;
+            else
+                nzeros = 0;
+            c >>= 32; // signed shift
+        }
+        assert c == 0L : c; // borrow out of subtract
+        assert dataInRangeIsZero(i, m, other); // negative result of subtract
+        return new FDBigInt( r, n-nzeros );
+    }
+
+    private static boolean dataInRangeIsZero(int i, int m, FDBigInt other) {
+        while ( i < m )
+            if (other.data[i++] != 0)
+                return false;
+        return true;
+    }
+
+    /*
+     * Compare FDBigInt with another FDBigInt. Return an integer
+     * >0: this > other
+     *  0: this == other
+     * <0: this < other
+     */
+    public int
+    cmp( FDBigInt other ){
+        int i;
+        if ( this.nWords > other.nWords ){
+            // if any of my high-order words is non-zero,
+            // then the answer is evident
+            int j = other.nWords-1;
+            for ( i = this.nWords-1; i > j ; i-- )
+                if ( this.data[i] != 0 ) return 1;
+        }else if ( this.nWords < other.nWords ){
+            // if any of other's high-order words is non-zero,
+            // then the answer is evident
+            int j = this.nWords-1;
+            for ( i = other.nWords-1; i > j ; i-- )
+                if ( other.data[i] != 0 ) return -1;
+        } else{
+            i = this.nWords-1;
+        }
+        for ( ; i > 0 ; i-- )
+            if ( this.data[i] != other.data[i] )
+                break;
+        // careful! want unsigned compare!
+        // use brute force here.
+        int a = this.data[i];
+        int b = other.data[i];
+        if ( a < 0 ){
+            // a is really big, unsigned
+            if ( b < 0 ){
+                return a-b; // both big, negative
+            } else {
+                return 1; // b not big, answer is obvious;
+            }
+        } else {
+            // a is not really big
+            if ( b < 0 ) {
+                // but b is really big
+                return -1;
+            } else {
+                return a - b;
+            }
+        }
+    }
+
+    /*
+     * Compute
+     * q = (int)( this / S )
+     * this = 10 * ( this mod S )
+     * Return q.
+     * This is the iteration step of digit development for output.
+     * We assume that S has been normalized, as above, and that
+     * "this" has been lshift'ed accordingly.
+     * Also assume, of course, that the result, q, can be expressed
+     * as an integer, 0 <= q < 10.
+     */
+    public int
+    quoRemIteration( FDBigInt S )throws IllegalArgumentException {
+        // ensure that this and S have the same number of
+        // digits. If S is properly normalized and q < 10 then
+        // this must be so.
+        if ( nWords != S.nWords ){
+            throw new IllegalArgumentException("disparate values");
+        }
+        // estimate q the obvious way. We will usually be
+        // right. If not, then we're only off by a little and
+        // will re-add.
+        int n = nWords-1;
+        long q = ((long)data[n]&0xffffffffL) / (long)S.data[n];
+        long diff = 0L;
+        for ( int i = 0; i <= n ; i++ ){
+            diff += ((long)data[i]&0xffffffffL) -  q*((long)S.data[i]&0xffffffffL);
+            data[i] = (int)diff;
+            diff >>= 32; // N.B. SIGNED shift.
+        }
+        if ( diff != 0L ) {
+            // damn, damn, damn. q is too big.
+            // add S back in until this turns +. This should
+            // not be very many times!
+            long sum = 0L;
+            while ( sum ==  0L ){
+                sum = 0L;
+                for ( int i = 0; i <= n; i++ ){
+                    sum += ((long)data[i]&0xffffffffL) +  ((long)S.data[i]&0xffffffffL);
+                    data[i] = (int) sum;
+                    sum >>= 32; // Signed or unsigned, answer is 0 or 1
+                }
+                /*
+                 * Originally the following line read
+                 * "if ( sum !=0 && sum != -1 )"
+                 * but that would be wrong, because of the
+                 * treatment of the two values as entirely unsigned,
+                 * it would be impossible for a carry-out to be interpreted
+                 * as -1 -- it would have to be a single-bit carry-out, or
+                 * +1.
+                 */
+                assert sum == 0 || sum == 1 : sum; // carry out of division correction
+                q -= 1;
+            }
+        }
+        // finally, we can multiply this by 10.
+        // it cannot overflow, right, as the high-order word has
+        // at least 4 high-order zeros!
+        long p = 0L;
+        for ( int i = 0; i <= n; i++ ){
+            p += 10*((long)data[i]&0xffffffffL);
+            data[i] = (int)p;
+            p >>= 32; // SIGNED shift.
+        }
+        assert p == 0L : p; // Carry out of *10
+        return (int)q;
+    }
+
+    public long
+    longValue(){
+        // if this can be represented as a long, return the value
+        assert this.nWords > 0 : this.nWords; // longValue confused
+
+        if (this.nWords == 1)
+            return ((long)data[0]&0xffffffffL);
+
+        assert dataInRangeIsZero(2, this.nWords, this); // value too big
+        assert data[1] >= 0;  // value too big
+        return ((long)(data[1]) << 32) | ((long)data[0]&0xffffffffL);
+    }
+
+    public String
+    toString() {
+        StringBuffer r = new StringBuffer(30);
+        r.append('[');
+        int i = Math.min( nWords-1, data.length-1) ;
+        if ( nWords > data.length ){
+            r.append( "("+data.length+"<"+nWords+"!)" );
+        }
+        for( ; i> 0 ; i-- ){
+            r.append( Integer.toHexString( data[i] ) );
+            r.append(' ');
+        }
+        r.append( Integer.toHexString( data[0] ) );
+        r.append(']');
+        return new String( r );
+    }
+}
--- a/src/share/classes/sun/misc/FloatingDecimal.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/misc/FloatingDecimal.java	Mon Nov 05 10:33:18 2012 -0500
@@ -2409,470 +2409,3 @@
 
 
 }
-
-/*
- * A really, really simple bigint package
- * tailored to the needs of floating base conversion.
- */
-class FDBigInt {
-    int nWords; // number of words used
-    int data[]; // value: data[0] is least significant
-
-
-    public FDBigInt( int v ){
-        nWords = 1;
-        data = new int[1];
-        data[0] = v;
-    }
-
-    public FDBigInt( long v ){
-        data = new int[2];
-        data[0] = (int)v;
-        data[1] = (int)(v>>>32);
-        nWords = (data[1]==0) ? 1 : 2;
-    }
-
-    public FDBigInt( FDBigInt other ){
-        data = new int[nWords = other.nWords];
-        System.arraycopy( other.data, 0, data, 0, nWords );
-    }
-
-    private FDBigInt( int [] d, int n ){
-        data = d;
-        nWords = n;
-    }
-
-    public FDBigInt( long seed, char digit[], int nd0, int nd ){
-        int n= (nd+8)/9;        // estimate size needed.
-        if ( n < 2 ) n = 2;
-        data = new int[n];      // allocate enough space
-        data[0] = (int)seed;    // starting value
-        data[1] = (int)(seed>>>32);
-        nWords = (data[1]==0) ? 1 : 2;
-        int i = nd0;
-        int limit = nd-5;       // slurp digits 5 at a time.
-        int v;
-        while ( i < limit ){
-            int ilim = i+5;
-            v = (int)digit[i++]-(int)'0';
-            while( i <ilim ){
-                v = 10*v + (int)digit[i++]-(int)'0';
-            }
-            multaddMe( 100000, v); // ... where 100000 is 10^5.
-        }
-        int factor = 1;
-        v = 0;
-        while ( i < nd ){
-            v = 10*v + (int)digit[i++]-(int)'0';
-            factor *= 10;
-        }
-        if ( factor != 1 ){
-            multaddMe( factor, v );
-        }
-    }
-
-    /*
-     * Left shift by c bits.
-     * Shifts this in place.
-     */
-    public void
-    lshiftMe( int c )throws IllegalArgumentException {
-        if ( c <= 0 ){
-            if ( c == 0 )
-                return; // silly.
-            else
-                throw new IllegalArgumentException("negative shift count");
-        }
-        int wordcount = c>>5;
-        int bitcount  = c & 0x1f;
-        int anticount = 32-bitcount;
-        int t[] = data;
-        int s[] = data;
-        if ( nWords+wordcount+1 > t.length ){
-            // reallocate.
-            t = new int[ nWords+wordcount+1 ];
-        }
-        int target = nWords+wordcount;
-        int src    = nWords-1;
-        if ( bitcount == 0 ){
-            // special hack, since an anticount of 32 won't go!
-            System.arraycopy( s, 0, t, wordcount, nWords );
-            target = wordcount-1;
-        } else {
-            t[target--] = s[src]>>>anticount;
-            while ( src >= 1 ){
-                t[target--] = (s[src]<<bitcount) | (s[--src]>>>anticount);
-            }
-            t[target--] = s[src]<<bitcount;
-        }
-        while( target >= 0 ){
-            t[target--] = 0;
-        }
-        data = t;
-        nWords += wordcount + 1;
-        // may have constructed high-order word of 0.
-        // if so, trim it
-        while ( nWords > 1 && data[nWords-1] == 0 )
-            nWords--;
-    }
-
-    /*
-     * normalize this number by shifting until
-     * the MSB of the number is at 0x08000000.
-     * This is in preparation for quoRemIteration, below.
-     * The idea is that, to make division easier, we want the
-     * divisor to be "normalized" -- usually this means shifting
-     * the MSB into the high words sign bit. But because we know that
-     * the quotient will be 0 < q < 10, we would like to arrange that
-     * the dividend not span up into another word of precision.
-     * (This needs to be explained more clearly!)
-     */
-    public int
-    normalizeMe() throws IllegalArgumentException {
-        int src;
-        int wordcount = 0;
-        int bitcount  = 0;
-        int v = 0;
-        for ( src= nWords-1 ; src >= 0 && (v=data[src]) == 0 ; src--){
-            wordcount += 1;
-        }
-        if ( src < 0 ){
-            // oops. Value is zero. Cannot normalize it!
-            throw new IllegalArgumentException("zero value");
-        }
-        /*
-         * In most cases, we assume that wordcount is zero. This only
-         * makes sense, as we try not to maintain any high-order
-         * words full of zeros. In fact, if there are zeros, we will
-         * simply SHORTEN our number at this point. Watch closely...
-         */
-        nWords -= wordcount;
-        /*
-         * Compute how far left we have to shift v s.t. its highest-
-         * order bit is in the right place. Then call lshiftMe to
-         * do the work.
-         */
-        if ( (v & 0xf0000000) != 0 ){
-            // will have to shift up into the next word.
-            // too bad.
-            for( bitcount = 32 ; (v & 0xf0000000) != 0 ; bitcount-- )
-                v >>>= 1;
-        } else {
-            while ( v <= 0x000fffff ){
-                // hack: byte-at-a-time shifting
-                v <<= 8;
-                bitcount += 8;
-            }
-            while ( v <= 0x07ffffff ){
-                v <<= 1;
-                bitcount += 1;
-            }
-        }
-        if ( bitcount != 0 )
-            lshiftMe( bitcount );
-        return bitcount;
-    }
-
-    /*
-     * Multiply a FDBigInt by an int.
-     * Result is a new FDBigInt.
-     */
-    public FDBigInt
-    mult( int iv ) {
-        long v = iv;
-        int r[];
-        long p;
-
-        // guess adequate size of r.
-        r = new int[ ( v * ((long)data[nWords-1]&0xffffffffL) > 0xfffffffL ) ? nWords+1 : nWords ];
-        p = 0L;
-        for( int i=0; i < nWords; i++ ) {
-            p += v * ((long)data[i]&0xffffffffL);
-            r[i] = (int)p;
-            p >>>= 32;
-        }
-        if ( p == 0L){
-            return new FDBigInt( r, nWords );
-        } else {
-            r[nWords] = (int)p;
-            return new FDBigInt( r, nWords+1 );
-        }
-    }
-
-    /*
-     * Multiply a FDBigInt by an int and add another int.
-     * Result is computed in place.
-     * Hope it fits!
-     */
-    public void
-    multaddMe( int iv, int addend ) {
-        long v = iv;
-        long p;
-
-        // unroll 0th iteration, doing addition.
-        p = v * ((long)data[0]&0xffffffffL) + ((long)addend&0xffffffffL);
-        data[0] = (int)p;
-        p >>>= 32;
-        for( int i=1; i < nWords; i++ ) {
-            p += v * ((long)data[i]&0xffffffffL);
-            data[i] = (int)p;
-            p >>>= 32;
-        }
-        if ( p != 0L){
-            data[nWords] = (int)p; // will fail noisily if illegal!
-            nWords++;
-        }
-    }
-
-    /*
-     * Multiply a FDBigInt by another FDBigInt.
-     * Result is a new FDBigInt.
-     */
-    public FDBigInt
-    mult( FDBigInt other ){
-        // crudely guess adequate size for r
-        int r[] = new int[ nWords + other.nWords ];
-        int i;
-        // I think I am promised zeros...
-
-        for( i = 0; i < this.nWords; i++ ){
-            long v = (long)this.data[i] & 0xffffffffL; // UNSIGNED CONVERSION
-            long p = 0L;
-            int j;
-            for( j = 0; j < other.nWords; j++ ){
-                p += ((long)r[i+j]&0xffffffffL) + v*((long)other.data[j]&0xffffffffL); // UNSIGNED CONVERSIONS ALL 'ROUND.
-                r[i+j] = (int)p;
-                p >>>= 32;
-            }
-            r[i+j] = (int)p;
-        }
-        // compute how much of r we actually needed for all that.
-        for ( i = r.length-1; i> 0; i--)
-            if ( r[i] != 0 )
-                break;
-        return new FDBigInt( r, i+1 );
-    }
-
-    /*
-     * Add one FDBigInt to another. Return a FDBigInt
-     */
-    public FDBigInt
-    add( FDBigInt other ){
-        int i;
-        int a[], b[];
-        int n, m;
-        long c = 0L;
-        // arrange such that a.nWords >= b.nWords;
-        // n = a.nWords, m = b.nWords
-        if ( this.nWords >= other.nWords ){
-            a = this.data;
-            n = this.nWords;
-            b = other.data;
-            m = other.nWords;
-        } else {
-            a = other.data;
-            n = other.nWords;
-            b = this.data;
-            m = this.nWords;
-        }
-        int r[] = new int[ n ];
-        for ( i = 0; i < n; i++ ){
-            c += (long)a[i] & 0xffffffffL;
-            if ( i < m ){
-                c += (long)b[i] & 0xffffffffL;
-            }
-            r[i] = (int) c;
-            c >>= 32; // signed shift.
-        }
-        if ( c != 0L ){
-            // oops -- carry out -- need longer result.
-            int s[] = new int[ r.length+1 ];
-            System.arraycopy( r, 0, s, 0, r.length );
-            s[i++] = (int)c;
-            return new FDBigInt( s, i );
-        }
-        return new FDBigInt( r, i );
-    }
-
-    /*
-     * Subtract one FDBigInt from another. Return a FDBigInt
-     * Assert that the result is positive.
-     */
-    public FDBigInt
-    sub( FDBigInt other ){
-        int r[] = new int[ this.nWords ];
-        int i;
-        int n = this.nWords;
-        int m = other.nWords;
-        int nzeros = 0;
-        long c = 0L;
-        for ( i = 0; i < n; i++ ){
-            c += (long)this.data[i] & 0xffffffffL;
-            if ( i < m ){
-                c -= (long)other.data[i] & 0xffffffffL;
-            }
-            if ( ( r[i] = (int) c ) == 0 )
-                nzeros++;
-            else
-                nzeros = 0;
-            c >>= 32; // signed shift
-        }
-        assert c == 0L : c; // borrow out of subtract
-        assert dataInRangeIsZero(i, m, other); // negative result of subtract
-        return new FDBigInt( r, n-nzeros );
-    }
-
-    private static boolean dataInRangeIsZero(int i, int m, FDBigInt other) {
-        while ( i < m )
-            if (other.data[i++] != 0)
-                return false;
-        return true;
-    }
-
-    /*
-     * Compare FDBigInt with another FDBigInt. Return an integer
-     * >0: this > other
-     *  0: this == other
-     * <0: this < other
-     */
-    public int
-    cmp( FDBigInt other ){
-        int i;
-        if ( this.nWords > other.nWords ){
-            // if any of my high-order words is non-zero,
-            // then the answer is evident
-            int j = other.nWords-1;
-            for ( i = this.nWords-1; i > j ; i-- )
-                if ( this.data[i] != 0 ) return 1;
-        }else if ( this.nWords < other.nWords ){
-            // if any of other's high-order words is non-zero,
-            // then the answer is evident
-            int j = this.nWords-1;
-            for ( i = other.nWords-1; i > j ; i-- )
-                if ( other.data[i] != 0 ) return -1;
-        } else{
-            i = this.nWords-1;
-        }
-        for ( ; i > 0 ; i-- )
-            if ( this.data[i] != other.data[i] )
-                break;
-        // careful! want unsigned compare!
-        // use brute force here.
-        int a = this.data[i];
-        int b = other.data[i];
-        if ( a < 0 ){
-            // a is really big, unsigned
-            if ( b < 0 ){
-                return a-b; // both big, negative
-            } else {
-                return 1; // b not big, answer is obvious;
-            }
-        } else {
-            // a is not really big
-            if ( b < 0 ) {
-                // but b is really big
-                return -1;
-            } else {
-                return a - b;
-            }
-        }
-    }
-
-    /*
-     * Compute
-     * q = (int)( this / S )
-     * this = 10 * ( this mod S )
-     * Return q.
-     * This is the iteration step of digit development for output.
-     * We assume that S has been normalized, as above, and that
-     * "this" has been lshift'ed accordingly.
-     * Also assume, of course, that the result, q, can be expressed
-     * as an integer, 0 <= q < 10.
-     */
-    public int
-    quoRemIteration( FDBigInt S )throws IllegalArgumentException {
-        // ensure that this and S have the same number of
-        // digits. If S is properly normalized and q < 10 then
-        // this must be so.
-        if ( nWords != S.nWords ){
-            throw new IllegalArgumentException("disparate values");
-        }
-        // estimate q the obvious way. We will usually be
-        // right. If not, then we're only off by a little and
-        // will re-add.
-        int n = nWords-1;
-        long q = ((long)data[n]&0xffffffffL) / (long)S.data[n];
-        long diff = 0L;
-        for ( int i = 0; i <= n ; i++ ){
-            diff += ((long)data[i]&0xffffffffL) -  q*((long)S.data[i]&0xffffffffL);
-            data[i] = (int)diff;
-            diff >>= 32; // N.B. SIGNED shift.
-        }
-        if ( diff != 0L ) {
-            // damn, damn, damn. q is too big.
-            // add S back in until this turns +. This should
-            // not be very many times!
-            long sum = 0L;
-            while ( sum ==  0L ){
-                sum = 0L;
-                for ( int i = 0; i <= n; i++ ){
-                    sum += ((long)data[i]&0xffffffffL) +  ((long)S.data[i]&0xffffffffL);
-                    data[i] = (int) sum;
-                    sum >>= 32; // Signed or unsigned, answer is 0 or 1
-                }
-                /*
-                 * Originally the following line read
-                 * "if ( sum !=0 && sum != -1 )"
-                 * but that would be wrong, because of the
-                 * treatment of the two values as entirely unsigned,
-                 * it would be impossible for a carry-out to be interpreted
-                 * as -1 -- it would have to be a single-bit carry-out, or
-                 * +1.
-                 */
-                assert sum == 0 || sum == 1 : sum; // carry out of division correction
-                q -= 1;
-            }
-        }
-        // finally, we can multiply this by 10.
-        // it cannot overflow, right, as the high-order word has
-        // at least 4 high-order zeros!
-        long p = 0L;
-        for ( int i = 0; i <= n; i++ ){
-            p += 10*((long)data[i]&0xffffffffL);
-            data[i] = (int)p;
-            p >>= 32; // SIGNED shift.
-        }
-        assert p == 0L : p; // Carry out of *10
-        return (int)q;
-    }
-
-    public long
-    longValue(){
-        // if this can be represented as a long, return the value
-        assert this.nWords > 0 : this.nWords; // longValue confused
-
-        if (this.nWords == 1)
-            return ((long)data[0]&0xffffffffL);
-
-        assert dataInRangeIsZero(2, this.nWords, this); // value too big
-        assert data[1] >= 0;  // value too big
-        return ((long)(data[1]) << 32) | ((long)data[0]&0xffffffffL);
-    }
-
-    public String
-    toString() {
-        StringBuffer r = new StringBuffer(30);
-        r.append('[');
-        int i = Math.min( nWords-1, data.length-1) ;
-        if ( nWords > data.length ){
-            r.append( "("+data.length+"<"+nWords+"!)" );
-        }
-        for( ; i> 0 ; i-- ){
-            r.append( Integer.toHexString( data[i] ) );
-            r.append(' ');
-        }
-        r.append( Integer.toHexString( data[0] ) );
-        r.append(']');
-        return new String( r );
-    }
-}
--- a/src/share/classes/sun/misc/Service.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/misc/Service.java	Mon Nov 05 10:33:18 2012 -0500
@@ -284,12 +284,20 @@
             }
             String cn = nextName;
             nextName = null;
+            Class<?> c = null;
             try {
-                return service.cast(Class.forName(cn, true, loader).newInstance());
+                c = Class.forName(cn, false, loader);
             } catch (ClassNotFoundException x) {
                 fail(service,
                      "Provider " + cn + " not found");
-            } catch (Exception x) {
+            }
+            if (!service.isAssignableFrom(c)) {
+                fail(service,
+                     "Provider " + cn  + " not a subtype");
+            }
+            try {
+                return service.cast(c.newInstance());
+            } catch (Throwable x) {
                 fail(service,
                      "Provider " + cn + " could not be instantiated: " + x,
                      x);
--- a/src/share/classes/sun/net/httpserver/Event.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/net/httpserver/Event.java	Mon Nov 05 10:33:18 2012 -0500
@@ -36,11 +36,3 @@
         this.exchange = t;
     }
 }
-
-class WriteFinishedEvent extends Event {
-    WriteFinishedEvent (ExchangeImpl t) {
-        super (t);
-        assert !t.writefinished;
-        t.writefinished = true;
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/net/httpserver/WriteFinishedEvent.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,34 @@
+/*
+ * Copyright (c) 2005, 2010, 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.httpserver;
+
+class WriteFinishedEvent extends Event {
+    WriteFinishedEvent (ExchangeImpl t) {
+        super (t);
+        assert !t.writefinished;
+        t.writefinished = true;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/net/www/http/KeepAliveCleanerEntry.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,56 @@
+/*
+ * Copyright (c) 1996, 2011, 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.www.http;
+
+import java.io.*;
+
+class KeepAliveCleanerEntry
+{
+    KeepAliveStream kas;
+    HttpClient hc;
+
+    public KeepAliveCleanerEntry(KeepAliveStream kas, HttpClient hc) {
+        this.kas = kas;
+        this.hc = hc;
+    }
+
+    protected KeepAliveStream getKeepAliveStream() {
+        return kas;
+    }
+
+    protected HttpClient getHttpClient() {
+        return hc;
+    }
+
+    protected void setQueuedForCleanup() {
+        kas.queuedForCleanup = true;
+    }
+
+    protected boolean getQueuedForCleanup() {
+        return kas.queuedForCleanup;
+    }
+
+}
--- a/src/share/classes/sun/net/www/http/KeepAliveStream.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/net/www/http/KeepAliveStream.java	Mon Nov 05 10:33:18 2012 -0500
@@ -206,32 +206,3 @@
         closed = true;
     }
 }
-
-
-class KeepAliveCleanerEntry
-{
-    KeepAliveStream kas;
-    HttpClient hc;
-
-    public KeepAliveCleanerEntry(KeepAliveStream kas, HttpClient hc) {
-        this.kas = kas;
-        this.hc = hc;
-    }
-
-    protected KeepAliveStream getKeepAliveStream() {
-        return kas;
-    }
-
-    protected HttpClient getHttpClient() {
-        return hc;
-    }
-
-    protected void setQueuedForCleanup() {
-        kas.queuedForCleanup = true;
-    }
-
-    protected boolean getQueuedForCleanup() {
-        return kas.queuedForCleanup;
-    }
-
-}
--- a/src/share/classes/sun/net/www/protocol/gopher/GopherClient.java	Mon Nov 05 10:30:49 2012 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,357 +0,0 @@
-/*
- * Copyright (c) 1996, 2004, 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.www.protocol.gopher;
-
-import java.io.*;
-import java.util.*;
-import java.net.*;
-import sun.net.www.*;
-import sun.net.NetworkClient;
-import java.net.URL;
-import java.net.URLStreamHandler;
-
-import sun.security.action.GetBooleanAction;
-
-/** Class to maintain the state of a gopher fetch and handle the protocol */
-public class GopherClient extends NetworkClient implements Runnable {
-
-    /* The following three data members are left in for binary
-     * backwards-compatibility.  Unfortunately, HotJava sets them directly
-     * when it wants to change the settings.  The new design has us not
-     * cache these, so this is unnecessary, but eliminating the data members
-     * would break HJB 1.1 under JDK 1.2.
-     *
-     * These data members are not used, and their values are meaningless.
-     * REMIND:  Take them out for JDK 2.0!
-     */
-
-    /**
-     * @deprecated
-     */
-    @Deprecated
-    public static boolean       useGopherProxy;
-
-    /**
-     * @deprecated
-     */
-    @Deprecated
-    public static String        gopherProxyHost;
-
-    /**
-     * @deprecated
-     */
-    @Deprecated
-    public static int           gopherProxyPort;
-
-
-    static {
-        useGopherProxy = java.security.AccessController.doPrivileged(
-            new sun.security.action.GetBooleanAction("gopherProxySet"))
-            .booleanValue();
-
-        gopherProxyHost = java.security.AccessController.doPrivileged(
-            new sun.security.action.GetPropertyAction("gopherProxyHost"));
-
-        gopherProxyPort = java.security.AccessController.doPrivileged(
-            new sun.security.action.GetIntegerAction("gopherProxyPort", 80))
-            .intValue();
-    }
-
-    PipedOutputStream os;
-    URL u;
-    int gtype;
-    String gkey;
-    sun.net.www.URLConnection connection;
-
-    GopherClient(sun.net.www.URLConnection connection) {
-        this.connection = connection;
-    }
-
-    /**
-     * @return true if gopher connections should go through a proxy, according
-     *          to system properties.
-     */
-    public static boolean getUseGopherProxy() {
-        return java.security.AccessController.doPrivileged(
-            new GetBooleanAction("gopherProxySet")).booleanValue();
-    }
-
-    /**
-     * @return the proxy host to use, or null if nothing is set.
-     */
-    public static String getGopherProxyHost() {
-        String host = java.security.AccessController.doPrivileged(
-                new sun.security.action.GetPropertyAction("gopherProxyHost"));
-        if ("".equals(host)) {
-            host = null;
-        }
-        return host;
-    }
-
-    /**
-     * @return the proxy port to use.  Will default reasonably.
-     */
-    public static int getGopherProxyPort() {
-        return java.security.AccessController.doPrivileged(
-            new sun.security.action.GetIntegerAction("gopherProxyPort", 80))
-            .intValue();
-    }
-
-    /** Given a url, setup to fetch the gopher document it refers to */
-    InputStream openStream(URL u) throws IOException {
-        this.u = u;
-        this.os = os;
-        int i = 0;
-        String s = u.getFile();
-        int limit = s.length();
-        int c = '1';
-        while (i < limit && (c = s.charAt(i)) == '/')
-            i++;
-        gtype = c == '/' ? '1' : c;
-        if (i < limit)
-            i++;
-        gkey = s.substring(i);
-
-        openServer(u.getHost(), u.getPort() <= 0 ? 70 : u.getPort());
-
-        MessageHeader msgh = new MessageHeader();
-
-        switch (gtype) {
-          case '0':
-          case '7':
-            msgh.add("content-type", "text/plain");
-            break;
-          case '1':
-            msgh.add("content-type", "text/html");
-            break;
-          case 'g':
-          case 'I':
-            msgh.add("content-type", "image/gif");
-            break;
-          default:
-            msgh.add("content-type", "content/unknown");
-            break;
-        }
-        if (gtype != '7') {
-            serverOutput.print(decodePercent(gkey) + "\r\n");
-            serverOutput.flush();
-        } else if ((i = gkey.indexOf('?')) >= 0) {
-            serverOutput.print(decodePercent(gkey.substring(0, i) + "\t" +
-                                           gkey.substring(i + 1) + "\r\n"));
-            serverOutput.flush();
-            msgh.add("content-type", "text/html");
-        } else {
-            msgh.add("content-type", "text/html");
-        }
-        connection.setProperties(msgh);
-        if (msgh.findValue("content-type") == "text/html") {
-            os = new PipedOutputStream();
-            PipedInputStream ret = new PipedInputStream();
-            ret.connect(os);
-            new Thread(this).start();
-            return ret;
-        }
-        return new GopherInputStream(this, serverInput);
-    }
-
-    /** Translate all the instances of %NN into the character they represent */
-    private String decodePercent(String s) {
-        if (s == null || s.indexOf('%') < 0)
-            return s;
-        int limit = s.length();
-        char d[] = new char[limit];
-        int dp = 0;
-        for (int sp = 0; sp < limit; sp++) {
-            int c = s.charAt(sp);
-            if (c == '%' && sp + 2 < limit) {
-                int s1 = s.charAt(sp + 1);
-                int s2 = s.charAt(sp + 2);
-                if ('0' <= s1 && s1 <= '9')
-                    s1 = s1 - '0';
-                else if ('a' <= s1 && s1 <= 'f')
-                    s1 = s1 - 'a' + 10;
-                else if ('A' <= s1 && s1 <= 'F')
-                    s1 = s1 - 'A' + 10;
-                else
-                    s1 = -1;
-                if ('0' <= s2 && s2 <= '9')
-                    s2 = s2 - '0';
-                else if ('a' <= s2 && s2 <= 'f')
-                    s2 = s2 - 'a' + 10;
-                else if ('A' <= s2 && s2 <= 'F')
-                    s2 = s2 - 'A' + 10;
-                else
-                    s2 = -1;
-                if (s1 >= 0 && s2 >= 0) {
-                    c = (s1 << 4) | s2;
-                    sp += 2;
-                }
-            }
-            d[dp++] = (char) c;
-        }
-        return new String(d, 0, dp);
-    }
-
-    /** Turn special characters into the %NN form */
-    private String encodePercent(String s) {
-        if (s == null)
-            return s;
-        int limit = s.length();
-        char d[] = null;
-        int dp = 0;
-        for (int sp = 0; sp < limit; sp++) {
-            int c = s.charAt(sp);
-            if (c <= ' ' || c == '"' || c == '%') {
-                if (d == null)
-                    d = s.toCharArray();
-                if (dp + 3 >= d.length) {
-                    char nd[] = new char[dp + 10];
-                    System.arraycopy(d, 0, nd, 0, dp);
-                    d = nd;
-                }
-                d[dp] = '%';
-                int dig = (c >> 4) & 0xF;
-                d[dp + 1] = (char) (dig < 10 ? '0' + dig : 'A' - 10 + dig);
-                dig = c & 0xF;
-                d[dp + 2] = (char) (dig < 10 ? '0' + dig : 'A' - 10 + dig);
-                dp += 3;
-            } else {
-                if (d != null) {
-                    if (dp >= d.length) {
-                        char nd[] = new char[dp + 10];
-                        System.arraycopy(d, 0, nd, 0, dp);
-                        d = nd;
-                    }
-                    d[dp] = (char) c;
-                }
-                dp++;
-            }
-        }
-        return d == null ? s : new String(d, 0, dp);
-    }
-
-    /** This method is run as a seperate thread when an incoming gopher
-        document requires translation to html */
-    public void run() {
-        int qpos = -1;
-        try {
-            if (gtype == '7' && (qpos = gkey.indexOf('?')) < 0) {
-                PrintStream ps = new PrintStream(os, false, encoding);
-                ps.print("<html><head><title>Searchable Gopher Index</title></head>\n<body><h1>Searchable Gopher Index</h1><isindex>\n</body></html>\n");
-            } else if (gtype != '1' && gtype != '7') {
-                byte buf[] = new byte[2048];
-                try {
-                    int n;
-                    while ((n = serverInput.read(buf)) >= 0)
-                            os.write(buf, 0, n);
-                } catch(Exception e) {
-                }
-            } else {
-                PrintStream ps = new PrintStream(os, false, encoding);
-                String title = null;
-                if (gtype == '7')
-                    title = "Results of searching for \"" + gkey.substring(qpos + 1)
-                        + "\" on " + u.getHost();
-                else
-                    title = "Gopher directory " + gkey + " from " + u.getHost();
-                ps.print("<html><head><title>");
-                ps.print(title);
-                ps.print("</title></head>\n<body>\n<H1>");
-                ps.print(title);
-                ps.print("</h1><dl compact>\n");
-                BufferedReader ds = new BufferedReader(new InputStreamReader(serverInput));
-                String s;
-                while ((s = ds.readLine()) != null) {
-                    int len = s.length();
-                    while (len > 0 && s.charAt(len - 1) <= ' ')
-                        len--;
-                    if (len <= 0)
-                        continue;
-                    int key = s.charAt(0);
-                    int t1 = s.indexOf('\t');
-                    int t2 = t1 > 0 ? s.indexOf('\t', t1 + 1) : -1;
-                    int t3 = t2 > 0 ? s.indexOf('\t', t2 + 1) : -1;
-                    if (t3 < 0) {
-                        // ps.print("<br><i>"+s+"</i>\n");
-                        continue;
-                    }
-                    String port = t3 + 1 < len ? ":" + s.substring(t3 + 1, len) : "";
-                    String host = t2 + 1 < t3 ? s.substring(t2 + 1, t3) : u.getHost();
-                    ps.print("<dt><a href=\"gopher://" + host + port + "/"
-                             + s.substring(0, 1) + encodePercent(s.substring(t1 + 1, t2)) + "\">\n");
-                    ps.print("<img align=middle border=0 width=25 height=32 src=");
-                    switch (key) {
-                      default:
-                        ps.print(System.getProperty("java.net.ftp.imagepath.file"));
-                        break;
-                      case '0':
-                        ps.print(System.getProperty("java.net.ftp.imagepath.text"));
-                        break;
-                      case '1':
-                        ps.print(System.getProperty("java.net.ftp.imagepath.directory"));
-                        break;
-                      case 'g':
-                        ps.print(System.getProperty("java.net.ftp.imagepath.gif"));
-                        break;
-                    }
-                    ps.print(".gif align=middle><dd>\n");
-                    ps.print(s.substring(1, t1) + "</a>\n");
-                }
-                ps.print("</dl></body>\n");
-                ps.close();
-           }
-
-       } catch (UnsupportedEncodingException e) {
-            throw new InternalError(encoding+ " encoding not found", e);
-       } catch (IOException e) {
-       } finally {
-           try {
-               closeServer();
-               os.close();
-           } catch (IOException e2) {
-           }
-        }
-    }
-}
-
-/** An input stream that does nothing more than hold on to the NetworkClient
-    that created it.  This is used when only the input stream is needed, and
-    the network client needs to be closed when the input stream is closed. */
-class GopherInputStream extends FilterInputStream {
-    NetworkClient parent;
-
-    GopherInputStream(NetworkClient o, InputStream fd) {
-        super(fd);
-        parent = o;
-    }
-
-    public void close() {
-        try {
-            parent.closeServer();
-            super.close();
-        } catch (IOException e) {
-        }
-    }
-}
--- a/src/share/classes/sun/net/www/protocol/gopher/Handler.java	Mon Nov 05 10:30:49 2012 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,100 +0,0 @@
-/*
- * Copyright (c) 1995, 2003, 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.www.protocol.gopher;
-
-import java.io.*;
-import java.util.*;
-import sun.net.NetworkClient;
-import java.net.URL;
-import java.net.URLStreamHandler;
-import java.net.Proxy;
-import java.net.InetSocketAddress;
-import java.net.SocketPermission;
-import java.security.Permission;
-import sun.net.www.protocol.http.HttpURLConnection;
-
-/**
- * A class to handle the gopher protocol.
- */
-
-public class Handler extends java.net.URLStreamHandler {
-
-    protected int getDefaultPort() {
-        return 70;
-    }
-
-    public java.net.URLConnection openConnection(URL u)
-    throws IOException {
-        return openConnection(u, null);
-    }
-
-    public java.net.URLConnection openConnection(URL u, Proxy p)
-    throws IOException {
-
-
-        /* if set for proxy usage then go through the http code to get */
-        /* the url connection. */
-        if (p == null && GopherClient.getUseGopherProxy()) {
-            String host = GopherClient.getGopherProxyHost();
-            if (host != null) {
-                InetSocketAddress saddr = InetSocketAddress.createUnresolved(host, GopherClient.getGopherProxyPort());
-
-                p = new Proxy(Proxy.Type.HTTP, saddr);
-            }
-        }
-        if (p != null) {
-            return new HttpURLConnection(u, p);
-        }
-
-        return new GopherURLConnection(u);
-    }
-}
-
-class GopherURLConnection extends sun.net.www.URLConnection {
-
-    Permission permission;
-
-    GopherURLConnection(URL u) {
-        super(u);
-    }
-
-    public void connect() throws IOException {
-    }
-
-    public InputStream getInputStream() throws IOException {
-        return new GopherClient(this).openStream(url);
-    }
-
-    public Permission getPermission() {
-        if (permission == null) {
-            int port = url.getPort();
-            port = port < 0 ? 70 : port;
-            String host = url.getHost() + ":" + url.getPort();
-            permission = new SocketPermission(host, "connect");
-        }
-        return permission;
-    }
-}
--- a/src/share/classes/sun/rmi/registry/RegistryImpl.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/rmi/registry/RegistryImpl.java	Mon Nov 05 10:33:18 2012 -0500
@@ -405,7 +405,8 @@
          */
         perms.add(new SocketPermission("*", "connect,accept"));
 
-        perms.add(new RuntimePermission("accessClassInPackage.sun.*"));
+        perms.add(new RuntimePermission("accessClassInPackage.sun.jvmstat.*"));
+        perms.add(new RuntimePermission("accessClassInPackage.sun.jvm.hotspot.*"));
 
         perms.add(new FilePermission("<<ALL FILES>>", "read"));
 
--- a/src/share/classes/sun/security/krb5/Checksum.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/Checksum.java	Mon Nov 05 10:33:18 2012 -0500
@@ -74,14 +74,18 @@
 
     private static boolean DEBUG = Krb5.DEBUG;
     static {
+        initStatic();
+    }
+
+    public static void initStatic() {
         String temp = null;
         Config cfg = null;
         try {
             cfg = Config.getInstance();
-            temp = cfg.getDefault("default_checksum", "libdefaults");
+            temp = cfg.get("libdefaults", "default_checksum");
             if (temp != null)
                 {
-                    CKSUMTYPE_DEFAULT = cfg.getType(temp);
+                    CKSUMTYPE_DEFAULT = Config.getType(temp);
                 } else {
                     /*
                      * If the default checksum is not
@@ -103,10 +107,10 @@
 
 
         try {
-            temp = cfg.getDefault("safe_checksum_type", "libdefaults");
+            temp = cfg.get("libdefaults", "safe_checksum_type");
             if (temp != null)
                 {
-                    SAFECKSUMTYPE_DEFAULT = cfg.getType(temp);
+                    SAFECKSUMTYPE_DEFAULT = Config.getType(temp);
                 } else {
                     SAFECKSUMTYPE_DEFAULT = CKSUMTYPE_RSA_MD5_DES;
                 }
--- a/src/share/classes/sun/security/krb5/Config.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/Config.java	Mon Nov 05 10:33:18 2012 -0500
@@ -38,11 +38,14 @@
 import java.io.BufferedReader;
 import java.io.InputStreamReader;
 import java.io.IOException;
-import java.util.Enumeration;
 import java.util.StringTokenizer;
 import java.net.InetAddress;
 import java.net.UnknownHostException;
+import java.security.AccessController;
+import java.security.PrivilegedExceptionAction;
+import java.util.Arrays;
 import java.util.List;
+import java.util.Locale;
 import sun.net.dns.ResolverConfiguration;
 import sun.security.krb5.internal.crypto.EType;
 import sun.security.krb5.internal.Krb5;
@@ -62,7 +65,7 @@
     /*
      * Hashtable used to store configuration infomation.
      */
-    private Hashtable<String,Object> stanzaTable;
+    private Hashtable<String,Object> stanzaTable = new Hashtable<>();
 
     private static boolean DEBUG = sun.security.krb5.internal.Krb5.DEBUG;
 
@@ -100,7 +103,9 @@
     /**
      * Refresh and reload the Configuration. This could involve,
      * for example reading the Configuration file again or getting
-     * the java.security.krb5.* system properties again.
+     * the java.security.krb5.* system properties again. This method
+     * also tries its best to update static fields in other classes
+     * that depend on the configuration.
      *
      * @exception KrbException if error occurs when constructing a Config
      * instance. Possible causes would be either of java.security.krb5.realm or
@@ -110,6 +115,8 @@
     public static synchronized void refresh() throws KrbException {
         singleton = new Config();
         KdcComm.initStatic();
+        EType.initStatic();
+        Checksum.initStatic();
     }
 
 
@@ -163,7 +170,7 @@
 
         // Always read the Kerberos configuration file
         try {
-            Vector<String> configFile;
+            List<String> configFile;
             String fileName = getJavaFileName();
             if (fileName != null) {
                 configFile = loadConfigFile(fileName);
@@ -194,61 +201,93 @@
                 }
             }
         } catch (IOException ioe) {
-            // No krb5.conf, no problem. We'll use DNS or system property etc.
+            // I/O error, mostly like krb5.conf missing.
+            // No problem. We'll use DNS or system property etc.
         }
     }
 
     /**
-     * Gets the default int value for the specified name.
-     * @param name the name.
-     * @return the default Integer, null is returned if no such name and
-     * value are found in configuration file, or error occurs when parsing
-     * string to integer.
+     * Gets the last-defined string value for the specified keys.
+     * @param keys the keys, as an array from section name, sub-section names
+     * (if any), to value name.
+     * @return the value. When there are multiple values for the same key,
+     * returns the last one. {@code null} is returned if not all the keys are
+     * defined. For example, {@code get("libdefaults", "forwardable")} will
+     * return null if "forwardable" is not defined in [libdefaults], and
+     * {@code get("realms", "R", "kdc")} will return null if "R" is not
+     * defined in [realms] or "kdc" is not defined for "R".
+     * @throws IllegalArgumentException if any of the keys is illegal, either
+     * because a key not the last one is not a (sub)section name or the last
+     * key is still a section name. For example, {@code get("libdefaults")}
+     * throws this exception because [libdefaults] is a section name instead of
+     * a value name, and {@code get("libdefaults", "forwardable", "tail")}
+     * also throws this exception because "forwardable" is already a value name
+     * and has no sub-key at all (given "forwardable" is defined, otherwise,
+     * this method has no knowledge if it's a value name or a section name),
+     */
+    @SuppressWarnings("unchecked")
+    public String get(String... keys) {
+        Vector<String> v = get0(keys);
+        if (v == null) return null;
+        return v.lastElement();
+    }
+
+    /**
+     * Gets all values for the specified keys.
+     * @see #get(java.lang.String[])
      */
-    public int getDefaultIntValue(String name) {
-        String result = null;
+    public String getAll(String... keys) {
+        Vector<String> v = get0(keys);
+        if (v == null) return null;
+        StringBuilder sb = new StringBuilder();
+        boolean first = true;
+        for (String s: v) {
+            if (first) {
+                sb.append(s);
+                first = false;
+            } else {
+                sb.append(' ').append(s);
+            }
+        }
+        return sb.toString();
+    }
+
+    // Internal method. Returns the vector of strings for keys.
+    // The only method (except for toString) that reads stanzaTable directly.
+    @SuppressWarnings("unchecked")
+    private Vector<String> get0(String... keys) {
+        Object current = stanzaTable;
+        try {
+            for (String key: keys) {
+                current = ((Hashtable<String,Object>)current).get(key);
+                if (current == null) return null;
+            }
+            return (Vector<String>)current;
+        } catch (ClassCastException cce) {
+            throw new IllegalArgumentException(cce);
+        }
+    }
+
+    /**
+     * Gets the int value for the specified keys.
+     * @param keys the keys
+     * @return the int value, Integer.MIN_VALUE is returned if it cannot be
+     * found or the value is not a legal integer.
+     * @throw IllegalArgumentException if any of the keys is illegal
+     * @see #get(java.lang.String[])
+     */
+    public int getIntValue(String... keys) {
+        String result = get(keys);
         int value = Integer.MIN_VALUE;
-        result = getDefault(name);
         if (result != null) {
             try {
                 value = parseIntValue(result);
             } catch (NumberFormatException e) {
                 if (DEBUG) {
                     System.out.println("Exception in getting value of " +
-                                       name + " " +
+                                       Arrays.toString(keys) + " " +
                                        e.getMessage());
-                    System.out.println("Setting " + name +
-                                       " to minimum value");
-                }
-                value = Integer.MIN_VALUE;
-            }
-        }
-        return value;
-    }
-
-    /**
-     * Gets the default int value for the specified name in the specified
-     * section. <br>This method is quicker by using section name as the
-     * search key.
-     * @param name the name.
-     * @param sectio the name string of the section.
-     * @return the default Integer, null is returned if no such name and
-     * value are found in configuration file, or error occurs when parsing
-     * string to integer.
-     */
-    public int getDefaultIntValue(String name, String section) {
-        String result = null;
-        int value = Integer.MIN_VALUE;
-        result = getDefault(name, section);
-        if (result != null) {
-            try {
-                value = parseIntValue(result);
-            } catch (NumberFormatException e) {
-                if (DEBUG) {
-                    System.out.println("Exception in getting value of " +
-                                       name +" in section " +
-                                       section + " "  + e.getMessage());
-                    System.out.println("Setting " + name +
+                    System.out.println("Setting " + Arrays.toString(keys) +
                                        " to minimum value");
                 }
                 value = Integer.MIN_VALUE;
@@ -258,152 +297,15 @@
     }
 
     /**
-     * Gets the default string value for the specified name.
-     * @param name the name.
-     * @return the default value, null is returned if it cannot be found.
-     */
-    public String getDefault(String name) {
-        if (stanzaTable == null) {
-            return null;
-        } else {
-            return getDefault(name, stanzaTable);
-        }
-    }
-
-    /**
-     * This method does the real job to recursively search through the
-     * stanzaTable.
-     * @param k the key string.
-     * @param t stanzaTable or sub hashtable within it.
-     * @return the value found in config file, returns null if no value
-     * matched with the key is found.
-     */
-    private String getDefault(String k, Hashtable<String, Object> t) {
-        String result = null;
-        String key;
-        if (stanzaTable != null) {
-            for (Enumeration<String> e = t.keys(); e.hasMoreElements(); ) {
-                key = e.nextElement();
-                Object ob = t.get(key);
-                if (ob instanceof Hashtable) {
-                    @SuppressWarnings("unchecked") // Checked with an instanceof check
-                    Hashtable<String, Object> table =
-                            (Hashtable<String, Object>)ob;
-                    result = getDefault(k, table);
-                    if (result != null) {
-                        return result;
-                    }
-                } else if (key.equalsIgnoreCase(k)) {
-                    if (ob instanceof String) {
-                        return (String)(t.get(key));
-                    } else if (ob instanceof Vector) {
-                        result = "";
-                        int length = ((Vector)ob).size();
-                        for (int i = 0; i < length; i++) {
-                            if (i == length -1) {
-                                result +=
-                                    (String)(((Vector)ob).elementAt(i));
-                            } else {
-                                result +=
-                                    (String)(((Vector)ob).elementAt(i)) + " ";
-                            }
-                        }
-                        return result;
-                    }
-                }
-            }
-        }
-        return result;
-    }
-
-    /**
-     * Gets the default string value for the specified name in the
-     * specified section.
-     * <br>This method is quicker by using the section name as the search key.
-     * @param name the name.
-     * @param section the name of the section.
-     * @return the default value, null is returned if it cannot be found.
+     * Gets the boolean value for the specified keys.
+     * @param keys the keys
+     * @return the boolean value, false is returned if it cannot be
+     * found or the value is not "true" (case insensitive).
+     * @throw IllegalArgumentException if any of the keys is illegal
+     * @see #get(java.lang.String[])
      */
-    // stanzaTable leads to a lot of unchecked casts since its value type is
-    // STANZATABLE = String | Hashtable<String, STANZATABLE>
-    @SuppressWarnings("unchecked")
-    public String getDefault(String name, String section) {
-        String stanzaName;
-        String result = null;
-        Hashtable<String, Object> subTable;
-
-        if (stanzaTable != null) {
-            for (Enumeration<String> e = stanzaTable.keys();
-                 e.hasMoreElements(); ) {
-                stanzaName = e.nextElement();
-                subTable = (Hashtable<String, Object>)
-                        stanzaTable.get(stanzaName);
-                if (stanzaName.equalsIgnoreCase(section)) {
-                    if (subTable.containsKey(name)) {
-                        return (String)(subTable.get(name));
-                    }
-                } else if (subTable.containsKey(section)) {
-                    Object ob = subTable.get(section);
-                    if (ob instanceof Hashtable) {
-                        Hashtable<String, Object> temp =
-                                (Hashtable<String, Object>)ob;
-                        if (temp.containsKey(name)) {
-                            Object object = temp.get(name);
-                            if (object instanceof Vector) {
-                                result = "";
-                                int length = ((Vector)object).size();
-                                for (int i = 0; i < length; i++) {
-                                    if (i == length - 1)  {
-                                        result +=
-                                        (String)(((Vector)object).elementAt(i));
-                                    } else {
-                                        result +=
-                                        (String)(((Vector)object).elementAt(i))
-                                                + " ";
-                                    }
-                                }
-                            } else {
-                                result = (String)object;
-                            }
-                        }
-                    }
-                }
-            }
-        }
-        return result;
-    }
-
-    /**
-     * Gets the default boolean value for the specified name.
-     * @param name the name.
-     * @return the default boolean value, false is returned if it cannot be
-     * found.
-     */
-    public boolean getDefaultBooleanValue(String name) {
-        String val = null;
-        if (stanzaTable == null) {
-            val = null;
-        } else {
-            val = getDefault(name, stanzaTable);
-        }
-        if (val != null && val.equalsIgnoreCase("true")) {
-            return true;
-        } else {
-            return false;
-        }
-    }
-
-    /**
-     * Gets the default boolean value for the specified name in the
-     * specified section.
-     * <br>This method is quicker by using the section name as the search key.
-     * @param name the name.
-     * @param section the name of the section.
-     * @return the default boolean value, false is returned if it cannot be
-     * found.
-     */
-    public boolean getDefaultBooleanValue(String name, String section) {
-        String val = getDefault(name, section);
+    public boolean getBooleanValue(String... keys) {
+        String val = get(keys);
         if (val != null && val.equalsIgnoreCase("true")) {
             return true;
         } else {
@@ -528,29 +430,14 @@
     }
 
     /**
-     * Finds the matching value in the hashtable.
-     */
-    private String find(String key1, String key2) {
-        String result;
-        if ((stanzaTable != null) &&
-            ((result = (String)
-                (((Hashtable)(stanzaTable.get(key1))).get(key2))) != null)) {
-            return result;
-        } else {
-            return "";
-        }
-    }
-
-    /**
-     * Reads name/value pairs to the memory from the configuration
-     * file. The default location of the configuration file is in java home
-     * directory.
+     * Reads lines to the memory from the configuration file.
      *
      * Configuration file contains information about the default realm,
      * ticket parameters, location of the KDC and the admin server for
      * known realms, etc. The file is divided into sections. Each section
      * contains one or more name/value pairs with one pair per line. A
      * typical file would be:
+     * <pre>
      * [libdefaults]
      *          default_realm = EXAMPLE.COM
      *          default_tgs_enctypes = des-cbc-md5
@@ -568,128 +455,178 @@
      * [domain_realm]
      *          blue.sample.com = TEST.SAMPLE.COM
      *          .backup.com     = EXAMPLE.COM
-     *
-     * @params fileName the conf file, cannot be null
-     * @return the content, null if fileName is empty
-     * @throws IOException if there is an I/O or format error
+     * </pre>
+     * @return an ordered list of strings representing the config file after
+     * some initial processing, including:<ol>
+     * <li> Comment lines and empty lines are removed
+     * <li> "{" not at the end of a line is appended to the previous line
+     * <li> The content of a section is also placed between "{" and "}".
+     * <li> Lines are trimmed</ol>
+     * @throws IOException if there is an I/O error
+     * @throws KrbException if there is a file format error
      */
-    private Vector<String> loadConfigFile(final String fileName) throws IOException {
+    private List<String> loadConfigFile(final String fileName)
+            throws IOException, KrbException {
         try {
-            if (!fileName.equals("")) {
-                BufferedReader br = new BufferedReader(new InputStreamReader(
-                java.security.AccessController.doPrivileged(
-                new java.security.PrivilegedExceptionAction<FileInputStream> () {
-                public FileInputStream run() throws IOException {
-                    return new FileInputStream(fileName);
-                }
-                })));
-                String Line;
-                Vector<String> v = new Vector<>();
+            List<String> v = new ArrayList<>();
+            try (BufferedReader br = new BufferedReader(new InputStreamReader(
+                AccessController.doPrivileged(
+                    new PrivilegedExceptionAction<FileInputStream> () {
+                        public FileInputStream run() throws IOException {
+                            return new FileInputStream(fileName);
+                        }
+                    })))) {
+                String line;
                 String previous = null;
-                while ((Line = br.readLine()) != null) {
-                    // ignore comments and blank line in the configuration file.
-                    // Comments start with #.
-                    if (!(Line.startsWith("#") || Line.trim().isEmpty())) {
-                        String current = Line.trim();
-                        // In practice, a subsection might look like:
-                        //      EXAMPLE.COM =
-                        //      {
-                        //              kdc = kerberos.example.com
-                        //              ...
-                        //      }
-                        // Before parsed into stanza table, it needs to be
-                        // converted into formal style:
-                        //      EXAMPLE.COM = {
-                        //              kdc = kerberos.example.com
-                        //              ...
-                        //      }
-                        //
-                        // So, if a line is "{", adhere to the previous line.
-                        if (current.equals("{")) {
-                            if (previous == null) {
-                                throw new IOException(
-                                    "Config file should not start with \"{\"");
-                            }
-                            previous += " " + current;
-                        } else {
-                            if (previous != null) {
-                                v.addElement(previous);
-                            }
-                            previous = current;
+                while ((line = br.readLine()) != null) {
+                    line = line.trim();
+                    if (line.startsWith("#") || line.isEmpty()) {
+                        // ignore comments and blank line
+                        // Comments start with #.
+                        continue;
+                    }
+                    // In practice, a subsection might look like:
+                    //      [realms]
+                    //      EXAMPLE.COM =
+                    //      {
+                    //          kdc = kerberos.example.com
+                    //          ...
+                    //      }
+                    // Before parsed into stanza table, it needs to be
+                    // converted into a canonicalized style (no indent):
+                    //      realms = {
+                    //          EXAMPLE.COM = {
+                    //              kdc = kerberos.example.com
+                    //              ...
+                    //          }
+                    //      }
+                    //
+                    if (line.startsWith("[")) {
+                        if (!line.endsWith("]")) {
+                            throw new KrbException("Illegal config content:"
+                                    + line);
                         }
+                        if (previous != null) {
+                            v.add(previous);
+                            v.add("}");
+                        }
+                        String title = line.substring(
+                                1, line.length()-1).trim();
+                        if (title.isEmpty()) {
+                            throw new KrbException("Illegal config content:"
+                                    + line);
+                        }
+                        previous = title + " = {";
+                    } else if (line.startsWith("{")) {
+                        if (previous == null) {
+                            throw new KrbException(
+                                "Config file should not start with \"{\"");
+                        }
+                        previous += " {";
+                        if (line.length() > 1) {
+                            // { and content on the same line
+                            v.add(previous);
+                            previous = line.substring(1).trim();
+                        }
+                    } else {
+                        if (previous == null) {
+                            throw new KrbException(
+                                "Config file must starts with a section");
+                        }
+                        v.add(previous);
+                        previous = line;
                     }
                 }
                 if (previous != null) {
-                    v.addElement(previous);
+                    v.add(previous);
+                    v.add("}");
                 }
-
-                br.close();
-                return v;
             }
-            return null;
+            return v;
         } catch (java.security.PrivilegedActionException pe) {
             throw (IOException)pe.getException();
         }
     }
 
-
     /**
      * Parses stanza names and values from configuration file to
      * stanzaTable (Hashtable). Hashtable key would be stanza names,
      * (libdefaults, realms, domain_realms, etc), and the hashtable value
      * would be another hashtable which contains the key-value pairs under
-     * a stanza name.
+     * a stanza name. The value of this sub-hashtable can be another hashtable
+     * containing another sub-sub-section or a vector of strings for
+     * final values (even if there is only one value defined).
+     * <p>
+     * For duplicates section names, the latter overwrites the former. For
+     * duplicate value names, the values are in a vector in its appearing order.
+     * </ol>
+     * Please note that this behavior is Java traditional. and it is
+     * not the same as the MIT krb5 behavior, where:<ol>
+     * <li>Duplicated root sections will be merged
+     * <li>For duplicated sub-sections, the former overwrites the latter
+     * <li>Duplicate keys for values are always saved in a vector
+     * </ol>
+     * @param v the strings in the file, never null, might be empty
+     * @throws KrbException if there is a file format error
      */
-    private Hashtable<String,Object> parseStanzaTable(Vector<String> v) throws KrbException {
-        if (v == null) {
-            throw new KrbException("I/O error while reading" +
-                        " configuration file.");
-        }
-        Hashtable<String,Object> table = new Hashtable<>();
-        for (int i = 0; i < v.size(); i++) {
-            String line = v.elementAt(i).trim();
-            if (line.equalsIgnoreCase("[realms]")) {
-                for (int count = i + 1; count < v.size() + 1; count++) {
-                    // find the next stanza name
-                    if ((count == v.size()) ||
-                        (v.elementAt(count).startsWith("["))) {
-                        Hashtable<String,Hashtable<String,Vector<String>>> temp =
-                            new Hashtable<>();
-                        temp = parseRealmField(v, i + 1, count);
-                        table.put("realms", temp);
-                        i = count - 1;
-                        break;
-                    }
+    @SuppressWarnings("unchecked")
+    private Hashtable<String,Object> parseStanzaTable(List<String> v)
+            throws KrbException {
+        Hashtable<String,Object> current = stanzaTable;
+        for (String line: v) {
+            // There are 3 kinds of lines
+            // 1. a = b
+            // 2. a = {
+            // 3. }
+            if (line.equals("}")) {
+                // Go back to parent, see below
+                current = (Hashtable<String,Object>)current.remove(" PARENT ");
+                if (current == null) {
+                    throw new KrbException("Unmatched close brace");
                 }
-            } else if (line.equalsIgnoreCase("[capaths]")) {
-                for (int count = i + 1; count < v.size() + 1; count++) {
-                    // find the next stanza name
-                    if ((count == v.size()) ||
-                        (v.elementAt(count).startsWith("["))) {
-                        Hashtable<String,Hashtable<String,Vector<String>>> temp =
-                            new Hashtable<>();
-                        temp = parseRealmField(v, i + 1, count);
-                        table.put("capaths", temp);
-                        i = count - 1;
-                        break;
-                    }
+            } else {
+                int pos = line.indexOf('=');
+                if (pos < 0) {
+                    throw new KrbException("Illegal config content:" + line);
                 }
-            } else if (line.startsWith("[") && line.endsWith("]")) {
-                String key = line.substring(1, line.length() - 1);
-                for (int count = i + 1; count < v.size() + 1; count++) {
-                    // find the next stanza name
-                    if ((count == v.size()) ||
-                        (v.elementAt(count).startsWith("["))) {
-                        Hashtable<String,String> temp =
-                            parseField(v, i + 1, count);
-                        table.put(key, temp);
-                        i = count - 1;
-                        break;
+                String key = line.substring(0, pos).trim();
+                String value = trimmed(line.substring(pos+1));
+                if (value.equals("{")) {
+                    Hashtable<String,Object> subTable;
+                    if (current == stanzaTable) {
+                        key = key.toLowerCase(Locale.US);
                     }
+                    subTable = new Hashtable<>();
+                    current.put(key, subTable);
+                    // A special entry for its parent. Put whitespaces around,
+                    // so will never be confused with a normal key
+                    subTable.put(" PARENT ", current);
+                    current = subTable;
+                } else {
+                    Vector<String> values;
+                    if (current.containsKey(key)) {
+                        Object obj = current.get(key);
+                        // If a key first shows as a section and then a value,
+                        // this is illegal. However, we haven't really forbid
+                        // first value then section, which the final result
+                        // is a section.
+                        if (!(obj instanceof Vector)) {
+                            throw new KrbException("Key " + key
+                                    + "used for both value and section");
+                        }
+                        values = (Vector<String>)current.get(key);
+                    } else {
+                        values = new Vector<String>();
+                        current.put(key, values);
+                    }
+                    values.add(value);
                 }
             }
         }
-        return table;
+        if (current != stanzaTable) {
+            throw new KrbException("Not closed");
+        }
+        return current;
     }
 
     /**
@@ -807,158 +744,20 @@
 
     private static String trimmed(String s) {
         s = s.trim();
+        if (s.isEmpty()) return s;
         if (s.charAt(0) == '"' && s.charAt(s.length()-1) == '"' ||
                 s.charAt(0) == '\'' && s.charAt(s.length()-1) == '\'') {
             s = s.substring(1, s.length()-1).trim();
         }
         return s;
     }
-    /**
-     * Parses key-value pairs under a stanza name.
-     */
-    private Hashtable<String,String>  parseField(Vector<String> v, int start, int end) {
-        Hashtable<String,String> table = new Hashtable<>();
-        String line;
-        for (int i = start; i < end; i++) {
-            line = v.elementAt(i);
-            for (int j = 0; j < line.length(); j++) {
-                if (line.charAt(j) == '=') {
-                    String key = (line.substring(0, j)).trim();
-                    String value = trimmed(line.substring(j + 1));
-                    table.put(key, value);
-                    break;
-                }
-            }
-        }
-        return table;
-    }
-
-    /**
-     * Parses key-value pairs under [realms].  The key would be the realm
-     * name, the value would be another hashtable which contains
-     * information for the realm given within a pair of braces.
-     */
-    private Hashtable<String,Hashtable<String,Vector<String>>> parseRealmField(Vector<String> v, int start, int end) {
-        Hashtable<String,Hashtable<String,Vector<String>>> table = new Hashtable<>();
-        String line;
-        for (int i = start; i < end; i++) {
-            line = v.elementAt(i).trim();
-            if (line.endsWith("{")) {
-                String key = "";
-                for (int j = 0; j < line.length(); j++) {
-                    if (line.charAt(j) == '=') {
-                        key = line.substring(0, j).trim();
-                        // get the key
-                        break;
-                    }
-                }
-                for (int k = i + 1; k < end; k++) {
-                    boolean found = false;
-                    line = v.elementAt(k).trim();
-                    for (int l = 0; l < line.length(); l++) {
-                        if (line.charAt(l) == '}') {
-                            found = true;
-                            break;
-                        }
-                    }
-                    if (found == true) {
-                        Hashtable<String,Vector<String>> temp = parseRealmFieldEx(v, i + 1, k);
-                        table.put(key, temp);
-                        i = k;
-                        found = false;
-                        break;
-                    }
-
-                }
-            }
-        }
-        return table;
-    }
-
-    /**
-     * Parses key-value pairs within each braces under [realms].
-     */
-    private Hashtable<String,Vector<String>> parseRealmFieldEx(Vector<String> v, int start, int end) {
-        Hashtable<String,Vector<String>> table = new Hashtable<>();
-        Vector<String> keyVector = new Vector<>();
-        Vector<String> nameVector = new Vector<>();
-        String line = "";
-        String key;
-        for (int i = start; i < end; i++) {
-            line = v.elementAt(i);
-            for (int j = 0; j < line.length(); j++) {
-                if (line.charAt(j) == '=') {
-                    int index;
-                    key = line.substring(0, j).trim();
-                    if (! exists(key, keyVector)) {
-                        keyVector.addElement(key);
-                        nameVector = new Vector<String> ();
-                    } else {
-                        nameVector = table.get(key);
-                    }
-                    nameVector.addElement(trimmed(line.substring(j + 1)));
-                    table.put(key, nameVector);
-                    break;
-                }
-            }
-        }
-        return table;
-    }
-
-    /**
-     * Compares the key with the known keys to see if it exists.
-     */
-    private boolean exists(String key, Vector<String> v) {
-        boolean exists = false;
-        for (int i = 0; i < v.size(); i++) {
-            if (v.elementAt(i).equals(key)) {
-                exists = true;
-            }
-        }
-        return exists;
-    }
 
     /**
      * For testing purpose. This method lists all information being parsed from
      * the configuration file to the hashtable.
      */
     public void listTable() {
-        listTable(stanzaTable);
-    }
-
-    // stanzaTable leads to a lot of unchecked casts since its value type is
-    // STANZATABLE = String | Hashtable<String, STANZATABLE>
-    @SuppressWarnings("unchecked")
-    private void listTable(Hashtable<String, Object> table) {
-        Vector<String> v = new Vector<String>();
-        String key;
-        if (stanzaTable != null) {
-            for (Enumeration<String> e = table.keys(); e.hasMoreElements(); ) {
-                key = e.nextElement();
-                Object object = table.get(key);
-                if (table == stanzaTable) {
-                    System.out.println("[" + key + "]");
-                }
-                if (object instanceof Hashtable) {
-                    if (table != stanzaTable)
-                        System.out.println("\t" + key + " = {");
-                    listTable((Hashtable<String, Object>)object);
-                    if (table != stanzaTable)
-                        System.out.println("\t}");
-
-                } else if (object instanceof String) {
-                    System.out.println("\t" + key + " = " +
-                                (String)table.get(key));
-                } else if (object instanceof Vector) {
-                    v = (Vector<String>)object;
-                    for (int i = 0; i < v.size(); i++) {
-                        System.out.println("\t" + key + " = " + v.elementAt(i));
-                    }
-                }
-            }
-        } else {
-            System.out.println("Configuration file not found.");
-        }
+        System.out.println(this);
     }
 
     /**
@@ -967,7 +766,7 @@
      */
     public int[] defaultEtype(String enctypes) {
         String default_enctypes;
-        default_enctypes = getDefault(enctypes, "libdefaults");
+        default_enctypes = get("libdefaults", enctypes);
         String delim = " ";
         StringTokenizer st;
         int[] etype;
@@ -991,7 +790,7 @@
             ArrayList<Integer> ls = new ArrayList<>(len);
             int type;
             for (int i = 0; i < len; i++) {
-                type = getType(st.nextToken());
+                type = Config.getType(st.nextToken());
                 if ((type != -1) &&
                     (EType.isSupported(type))) {
                     ls.add(type);
@@ -1032,7 +831,7 @@
      * checksum type to int value that can be later used by EType and
      * Checksum classes.
      */
-    public int getType(String input) {
+    public static int getType(String input) {
         int result = -1;
         if (input == null) {
             return result;
@@ -1114,11 +913,11 @@
     public boolean useAddresses() {
         boolean useAddr = false;
         // use addresses if "no_addresses" is set to false
-        String value = getDefault("no_addresses", "libdefaults");
+        String value = get("libdefaults", "no_addresses");
         useAddr = (value != null && value.equalsIgnoreCase("false"));
         if (useAddr == false) {
             // use addresses if "noaddresses" is set to false
-            value = getDefault("noaddresses", "libdefaults");
+            value = get("libdefaults", "noaddresses");
             useAddr = (value != null && value.equalsIgnoreCase("false"));
         }
         return useAddr;
@@ -1127,10 +926,10 @@
     /**
      * Check if need to use DNS to locate Kerberos services
      */
-    public boolean useDNS(String name) {
-        String value = getDefault(name, "libdefaults");
+    private boolean useDNS(String name) {
+        String value = get("libdefaults", name);
         if (value == null) {
-            value = getDefault("dns_fallback", "libdefaults");
+            value = get("libdefaults", "dns_fallback");
             if ("false".equalsIgnoreCase(value)) {
                 return false;
             } else {
@@ -1144,14 +943,14 @@
     /**
      * Check if need to use DNS to locate the KDC
      */
-    public boolean useDNS_KDC() {
+    private boolean useDNS_KDC() {
         return useDNS("dns_lookup_kdc");
     }
 
     /*
      * Check if need to use DNS to locate the Realm
      */
-    public boolean useDNS_Realm() {
+    private boolean useDNS_Realm() {
         return useDNS("dns_lookup_realm");
     }
 
@@ -1165,7 +964,7 @@
             return defaultRealm;
         }
         Exception cause = null;
-        String realm = getDefault("default_realm", "libdefaults");
+        String realm = get("libdefaults", "default_realm");
         if ((realm == null) && useDNS_Realm()) {
             // use DNS to locate Kerberos realm
             try {
@@ -1212,7 +1011,7 @@
             return defaultKDC;
         }
         Exception cause = null;
-        String kdcs = getDefault("kdc", realm);
+        String kdcs = getAll("realms", realm, "kdc");
         if ((kdcs == null) && useDNS_KDC()) {
             // use DNS to locate KDC
             try {
--- a/src/share/classes/sun/security/krb5/KdcComm.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/KdcComm.java	Mon Nov 05 10:33:18 2012 -0500
@@ -142,11 +142,11 @@
 
         try {
             Config cfg = Config.getInstance();
-            String temp = cfg.getDefault("kdc_timeout", "libdefaults");
+            String temp = cfg.get("libdefaults", "kdc_timeout");
             timeout = parsePositiveIntString(temp);
-            temp = cfg.getDefault("max_retries", "libdefaults");
+            temp = cfg.get("libdefaults", "max_retries");
             max_retries = parsePositiveIntString(temp);
-            temp = cfg.getDefault("udp_preference_limit", "libdefaults");
+            temp = cfg.get("libdefaults", "udp_preference_limit");
             udf_pref_limit = parsePositiveIntString(temp);
         } catch (Exception exc) {
            // ignore any exceptions; use default values
@@ -421,7 +421,7 @@
         int temp = -1;
         try {
             String value =
-               Config.getInstance().getDefault(key, realm);
+               Config.getInstance().get("realms", realm, key);
             temp = parsePositiveIntString(value);
         } catch (Exception exc) {
             // Ignored, defValue will be picked up
--- a/src/share/classes/sun/security/krb5/PrincipalName.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/PrincipalName.java	Mon Nov 05 10:33:18 2012 -0500
@@ -655,19 +655,19 @@
         try {
             String subname = null;
             Config c = Config.getInstance();
-            if ((result = c.getDefault(name, "domain_realm")) != null)
+            if ((result = c.get("domain_realm", name)) != null)
                 return result;
             else {
                 for (int i = 1; i < name.length(); i++) {
                     if ((name.charAt(i) == '.') && (i != name.length() - 1)) { //mapping could be .ibm.com = AUSTIN.IBM.COM
                         subname = name.substring(i);
-                        result = c.getDefault(subname, "domain_realm");
+                        result = c.get("domain_realm", subname);
                         if (result != null) {
                             break;
                         }
                         else {
                             subname = name.substring(i + 1);      //or mapping could be ibm.com = AUSTIN.IBM.COM
-                            result = c.getDefault(subname, "domain_realm");
+                            result = c.get("domain_realm", subname);
                             if (result != null) {
                                 break;
                             }
--- a/src/share/classes/sun/security/krb5/Realm.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/Realm.java	Mon Nov 05 10:33:18 2012 -0500
@@ -350,7 +350,7 @@
             return null;
         }
 
-        String intermediaries = cfg.getDefault(sRealm, cRealm);
+        String intermediaries = cfg.getAll("capaths", cRealm, sRealm);
 
         if (intermediaries == null) {
             if (DEBUG) {
@@ -459,7 +459,7 @@
                                    tempTarget);
             }
 
-            intermediaries = cfg.getDefault(tempTarget, cRealm);
+            intermediaries = cfg.getAll("capaths", cRealm, tempTarget);
 
         } while (true);
 
--- a/src/share/classes/sun/security/krb5/SCDynamicStoreConfig.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/SCDynamicStoreConfig.java	Mon Nov 05 10:33:18 2012 -0500
@@ -34,19 +34,25 @@
 public class SCDynamicStoreConfig {
     private static native void installNotificationCallback();
     private static native Hashtable<String, Object> getKerberosConfig();
+    private static boolean DEBUG = sun.security.krb5.internal.Krb5.DEBUG;
 
     static {
-        java.security.AccessController.doPrivileged(
-            new java.security.PrivilegedAction<Void>() {
-                public Void run() {
-                    System.loadLibrary("osx");
-                    return null;
+        boolean isMac = java.security.AccessController.doPrivileged(
+            new java.security.PrivilegedAction<Boolean>() {
+                public Boolean run() {
+                    String osname = System.getProperty("os.name");
+                    if (osname.contains("OS X")) {
+                        System.loadLibrary("osx");
+                        return true;
+                    }
+                    return false;
                 }
             });
-        installNotificationCallback();
+        if (isMac) installNotificationCallback();
     }
 
-    private static Vector<String> unwrapHost(Collection<Hashtable<String, String>> c) {
+    private static Vector<String> unwrapHost(
+            Collection<Hashtable<String, String>> c) {
         Vector<String> vector = new Vector<String>();
         for (Hashtable<String, String> m : c) {
             vector.add(m.get("host"));
@@ -60,20 +66,25 @@
      * are wrapped inside Hashtables
      */
     @SuppressWarnings("unchecked")
-    private static Hashtable<String, Object> convertRealmConfigs(Hashtable<String, ?> configs) {
+    private static Hashtable<String, Object>
+            convertRealmConfigs(Hashtable<String, ?> configs) {
         Hashtable<String, Object> realmsTable = new Hashtable<String, Object>();
 
         for (String realm : configs.keySet()) {
             // get the kdc
-            Hashtable<String, Collection<?>> map = (Hashtable<String, Collection<?>>) configs.get(realm);
-            Collection<Hashtable<String, String>> kdc = (Collection<Hashtable<String, String>>) map.get("kdc");
+            Hashtable<String, Collection<?>> map =
+                    (Hashtable<String, Collection<?>>) configs.get(realm);
+            Hashtable<String, Vector<String>> realmMap =
+                    new Hashtable<String, Vector<String>>();
 
             // put the kdc into the realmMap
-            Hashtable<String, Vector<String>> realmMap = new Hashtable<String, Vector<String>>();
+            Collection<Hashtable<String, String>> kdc =
+                    (Collection<Hashtable<String, String>>) map.get("kdc");
             if (kdc != null) realmMap.put("kdc", unwrapHost(kdc));
 
             // put the admin server into the realmMap
-            Collection<Hashtable<String, String>> kadmin = (Collection<Hashtable<String, String>>) map.get("kadmin");
+            Collection<Hashtable<String, String>> kadmin =
+                    (Collection<Hashtable<String, String>>) map.get("kadmin");
             if (kadmin != null) realmMap.put("admin_server", unwrapHost(kadmin));
 
             // add the full entry to the realmTable
@@ -90,23 +101,44 @@
      * @return
      * @throws IOException
      */
-    @SuppressWarnings("unchecked")
     public static Hashtable<String, Object> getConfig() throws IOException {
         Hashtable<String, Object> stanzaTable = getKerberosConfig();
         if (stanzaTable == null) {
-            throw new IOException("Could not load configuration from SCDynamicStore");
+            throw new IOException(
+                    "Could not load configuration from SCDynamicStore");
         }
-        //System.out.println("Raw map from JNI: " + stanzaTable);
+        if (DEBUG) System.out.println("Raw map from JNI: " + stanzaTable);
+        return convertNativeConfig(stanzaTable);
+    }
 
+    @SuppressWarnings("unchecked")
+    private static Hashtable<String, Object> convertNativeConfig(
+            Hashtable<String, Object> stanzaTable) {
         // convert SCDynamicStore realm structure to Java realm structure
-        Hashtable<String, ?> realms = (Hashtable<String, ?>) stanzaTable.get("realms");
+        Hashtable<String, ?> realms =
+                (Hashtable<String, ?>) stanzaTable.get("realms");
         if (realms != null) {
             stanzaTable.remove("realms");
             Hashtable<String, Object> realmsTable = convertRealmConfigs(realms);
             stanzaTable.put("realms", realmsTable);
         }
-
-       // System.out.println("stanzaTable : " + stanzaTable);
+        WrapAllStringInVector(stanzaTable);
+        if (DEBUG) System.out.println("stanzaTable : " + stanzaTable);
         return stanzaTable;
     }
+
+    @SuppressWarnings("unchecked")
+    private static void WrapAllStringInVector(
+            Hashtable<String, Object> stanzaTable) {
+        for (String s: stanzaTable.keySet()) {
+            Object v = stanzaTable.get(s);
+            if (v instanceof Hashtable) {
+                WrapAllStringInVector((Hashtable<String,Object>)v);
+            } else if (v instanceof String) {
+                Vector<String> vec = new Vector<>();
+                vec.add((String)v);
+                stanzaTable.put(s, vec);
+            }
+        }
+    }
 }
--- a/src/share/classes/sun/security/krb5/internal/KDCOptions.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/internal/KDCOptions.java	Mon Nov 05 10:33:18 2012 -0500
@@ -120,9 +120,9 @@
 
 public class KDCOptions extends KerberosFlags {
 
-    public final int KDC_OPT_PROXIABLE = 0x10000000;
-    public final int KDC_OPT_RENEWABLE_OK = 0x00000010;
-    public final int KDC_OPT_FORWARDABLE = 0x40000000;
+    private static final int KDC_OPT_PROXIABLE = 0x10000000;
+    private static final int KDC_OPT_RENEWABLE_OK = 0x00000010;
+    private static final int KDC_OPT_FORWARDABLE = 0x40000000;
 
 
     // KDC Options
@@ -244,33 +244,31 @@
 
             Config config = Config.getInstance();
 
-            /*
-             * First see if the IBM hex format is being used.
-             * If not, try the Sun's string (boolean) format.
-             */
+            // If key not present, returns Integer.MIN_VALUE, which is
+            // almost all zero.
 
-            int options =config.getDefaultIntValue("kdc_default_options",
-                    "libdefaults");
+            int options = config.getIntValue("libdefaults",
+                    "kdc_default_options");
 
-            if ((options & RENEWABLE_OK) == RENEWABLE_OK) {
+            if ((options & KDC_OPT_RENEWABLE_OK) == KDC_OPT_RENEWABLE_OK) {
                 set(RENEWABLE_OK, true);
             } else {
-                if (config.getDefaultBooleanValue("renewable", "libdefaults")) {
+                if (config.getBooleanValue("libdefaults", "renewable")) {
                     set(RENEWABLE_OK, true);
                 }
             }
-            if ((options & PROXIABLE) == PROXIABLE) {
+            if ((options & KDC_OPT_PROXIABLE) == KDC_OPT_PROXIABLE) {
                 set(PROXIABLE, true);
             } else {
-                if (config.getDefaultBooleanValue("proxiable", "libdefaults")) {
+                if (config.getBooleanValue("libdefaults", "proxiable")) {
                     set(PROXIABLE, true);
                 }
             }
 
-            if ((options & FORWARDABLE) == FORWARDABLE) {
+            if ((options & KDC_OPT_FORWARDABLE) == KDC_OPT_FORWARDABLE) {
                 set(FORWARDABLE, true);
             } else {
-                if (config.getDefaultBooleanValue("forwardable", "libdefaults")) {
+                if (config.getBooleanValue("libdefaults", "forwardable")) {
                     set(FORWARDABLE, true);
                 }
             }
--- a/src/share/classes/sun/security/krb5/internal/KerberosTime.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/internal/KerberosTime.java	Mon Nov 05 10:33:18 2012 -0500
@@ -350,9 +350,9 @@
     public static int getDefaultSkew() {
         int tdiff = Krb5.DEFAULT_ALLOWABLE_CLOCKSKEW;
         try {
-            Config c = Config.getInstance();
-            if ((tdiff = c.getDefaultIntValue("clockskew",
-                                              "libdefaults")) == Integer.MIN_VALUE) {   //value is not defined
+            if ((tdiff = Config.getInstance().getIntValue(
+                    "libdefaults", "clockskew"))
+                        == Integer.MIN_VALUE) {   //value is not defined
                 tdiff = Krb5.DEFAULT_ALLOWABLE_CLOCKSKEW;
             }
         } catch (KrbException e) {
--- a/src/share/classes/sun/security/krb5/internal/ccache/FileCredentialsCache.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/internal/ccache/FileCredentialsCache.java	Mon Nov 05 10:33:18 2012 -0500
@@ -348,7 +348,7 @@
      * Returns path name of the credentials cache file.
      * The path name is searched in the following order:
      *
-     * 1. KRB5CCNAME
+     * 1. KRB5CCNAME (bare file name without FILE:)
      * 2. /tmp/krb5cc_<uid> on unix systems
      * 3. <user.home>/krb5cc_<user.name>
      * 4. <user.home>/krb5cc (if can't get <user.name>)
@@ -359,11 +359,19 @@
         String stdCacheNameComponent = "krb5cc";
         String name;
 
+        // The env var can start with TYPE:, we only support FILE: here.
+        // http://docs.oracle.com/cd/E19082-01/819-2252/6n4i8rtr3/index.html
         name = java.security.AccessController.doPrivileged(
                 new java.security.PrivilegedAction<String>() {
             @Override
             public String run() {
-                return System.getenv("KRB5CCNAME");
+                String cache = System.getenv("KRB5CCNAME");
+                if (cache != null &&
+                        (cache.length() >= 5) &&
+                        cache.regionMatches(true, 0, "FILE:", 0, 5)) {
+                    cache = cache.substring(5);
+                }
+                return cache;
             }
         });
         if (name != null) {
--- a/src/share/classes/sun/security/krb5/internal/crypto/CksumType.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/internal/crypto/CksumType.java	Mon Nov 05 10:33:18 2012 -0500
@@ -126,10 +126,10 @@
         int cksumType = Checksum.CKSUMTYPE_RSA_MD5; // default
         try {
             Config c = Config.getInstance();
-            if ((cksumType = (c.getType(c.getDefault("ap_req_checksum_type",
-                                "libdefaults")))) == - 1) {
-                if ((cksumType = c.getType(c.getDefault("checksum_type",
-                                "libdefaults"))) == -1) {
+            if ((cksumType = (Config.getType(c.get("libdefaults",
+                    "ap_req_checksum_type")))) == - 1) {
+                if ((cksumType = Config.getType(c.get("libdefaults",
+                        "checksum_type"))) == -1) {
                     cksumType = Checksum.CKSUMTYPE_RSA_MD5; // default
                 }
             }
--- a/src/share/classes/sun/security/krb5/internal/crypto/EType.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/internal/crypto/EType.java	Mon Nov 05 10:33:18 2012 -0500
@@ -48,13 +48,17 @@
 public abstract class EType {
 
     private static final boolean DEBUG = Krb5.DEBUG;
-    private static final boolean ALLOW_WEAK_CRYPTO;
+    private static boolean allowWeakCrypto;
 
     static {
+        initStatic();
+    }
+
+    public static void initStatic() {
         boolean allowed = true;
         try {
             Config cfg = Config.getInstance();
-            String temp = cfg.getDefault("allow_weak_crypto", "libdefaults");
+            String temp = cfg.get("libdefaults", "allow_weak_crypto");
             if (temp != null && temp.equals("false")) allowed = false;
         } catch (Exception exc) {
             if (DEBUG) {
@@ -63,7 +67,7 @@
                                     exc.getMessage());
             }
         }
-        ALLOW_WEAK_CRYPTO = allowed;
+        allowWeakCrypto = allowed;
     }
 
     public static EType getInstance  (int eTypeConst)
@@ -216,7 +220,7 @@
         } else {
             result = BUILTIN_ETYPES;
         }
-        if (!ALLOW_WEAK_CRYPTO) {
+        if (!allowWeakCrypto) {
             // The last 2 etypes are now weak ones
             return Arrays.copyOfRange(result, 0, result.length - 2);
         }
--- a/src/share/classes/sun/security/krb5/internal/ktab/KeyTab.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/krb5/internal/ktab/KeyTab.java	Mon Nov 05 10:33:18 2012 -0500
@@ -186,8 +186,8 @@
         } else {
             String kname = null;
             try {
-                String keytab_names = Config.getInstance().getDefault
-                    ("default_keytab_name", "libdefaults");
+                String keytab_names = Config.getInstance().get
+                        ("libdefaults", "default_keytab_name");
                 if (keytab_names != null) {
                     StringTokenizer st = new StringTokenizer(keytab_names, " ");
                     while (st.hasMoreTokens()) {
--- a/src/share/classes/sun/security/provider/SecureRandom.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/provider/SecureRandom.java	Mon Nov 05 10:33:18 2012 -0500
@@ -56,12 +56,6 @@
 
     private static final long serialVersionUID = 3581829991155417889L;
 
-    /**
-     * This static object will be seeded by SeedGenerator, and used
-     * to seed future instances of SecureRandom
-     */
-    private static SecureRandom seeder;
-
     private static final int DIGEST_SIZE = 20;
     private transient MessageDigest digest;
     private byte[] state;
@@ -173,6 +167,28 @@
     }
 
     /**
+     * This static object will be seeded by SeedGenerator, and used
+     * to seed future instances of SHA1PRNG SecureRandoms.
+     *
+     * Bloch, Effective Java Second Edition: Item 71
+     */
+    private static class SeederHolder {
+
+        private static final SecureRandom seeder;
+
+        static {
+            /*
+             * Call to SeedGenerator.generateSeed() to add additional
+             * seed material (likely from the Native implementation).
+             */
+            seeder = new SecureRandom(SeedGenerator.getSystemEntropy());
+            byte [] b = new byte[DIGEST_SIZE];
+            SeedGenerator.generateSeed(b);
+            seeder.engineSetSeed(b);
+        }
+    }
+
+    /**
      * Generates a user-specified number of random bytes.
      *
      * @param bytes the array to be filled in with random bytes.
@@ -183,13 +199,8 @@
         byte[] output = remainder;
 
         if (state == null) {
-            if (seeder == null) {
-                seeder = new SecureRandom(SeedGenerator.getSystemEntropy());
-                seeder.engineSetSeed(engineGenerateSeed(DIGEST_SIZE));
-            }
-
             byte[] seed = new byte[DIGEST_SIZE];
-            seeder.engineNextBytes(seed);
+            SeederHolder.seeder.engineNextBytes(seed);
             state = digest.digest(seed);
         }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/ExtensionType.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,101 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.util.ArrayList;
+import java.util.List;
+
+final class ExtensionType {
+
+    final int id;
+    final String name;
+
+    private ExtensionType(int id, String name) {
+        this.id = id;
+        this.name = name;
+    }
+
+    public String toString() {
+        return name;
+    }
+
+    static List<ExtensionType> knownExtensions = new ArrayList<ExtensionType>(9);
+
+    static ExtensionType get(int id) {
+        for (ExtensionType ext : knownExtensions) {
+            if (ext.id == id) {
+                return ext;
+            }
+        }
+        return new ExtensionType(id, "type_" + id);
+    }
+
+    private static ExtensionType e(int id, String name) {
+        ExtensionType ext = new ExtensionType(id, name);
+        knownExtensions.add(ext);
+        return ext;
+    }
+
+    // extensions defined in RFC 3546
+    final static ExtensionType EXT_SERVER_NAME =
+            e(0x0000, "server_name");            // IANA registry value: 0
+    final static ExtensionType EXT_MAX_FRAGMENT_LENGTH =
+            e(0x0001, "max_fragment_length");    // IANA registry value: 1
+    final static ExtensionType EXT_CLIENT_CERTIFICATE_URL =
+            e(0x0002, "client_certificate_url"); // IANA registry value: 2
+    final static ExtensionType EXT_TRUSTED_CA_KEYS =
+            e(0x0003, "trusted_ca_keys");        // IANA registry value: 3
+    final static ExtensionType EXT_TRUNCATED_HMAC =
+            e(0x0004, "truncated_hmac");         // IANA registry value: 4
+    final static ExtensionType EXT_STATUS_REQUEST =
+            e(0x0005, "status_request");         // IANA registry value: 5
+
+    // extensions defined in RFC 4681
+    final static ExtensionType EXT_USER_MAPPING =
+            e(0x0006, "user_mapping");           // IANA registry value: 6
+
+    // extensions defined in RFC 5081
+    final static ExtensionType EXT_CERT_TYPE =
+            e(0x0009, "cert_type");              // IANA registry value: 9
+
+    // extensions defined in RFC 4492 (ECC)
+    final static ExtensionType EXT_ELLIPTIC_CURVES =
+            e(0x000A, "elliptic_curves");        // IANA registry value: 10
+    final static ExtensionType EXT_EC_POINT_FORMATS =
+            e(0x000B, "ec_point_formats");       // IANA registry value: 11
+
+    // extensions defined in RFC 5054
+    final static ExtensionType EXT_SRP =
+            e(0x000C, "srp");                    // IANA registry value: 12
+
+    // extensions defined in RFC 5246
+    final static ExtensionType EXT_SIGNATURE_ALGORITHMS =
+            e(0x000D, "signature_algorithms");   // IANA registry value: 13
+
+    // extensions defined in RFC 5746
+    final static ExtensionType EXT_RENEGOTIATION_INFO =
+            e(0xff01, "renegotiation_info");     // IANA registry value: 65281
+}
--- a/src/share/classes/sun/security/ssl/HandshakeInStream.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/ssl/HandshakeInStream.java	Mon Nov 05 10:33:18 2012 -0500
@@ -191,6 +191,7 @@
 
     byte[] getBytes8() throws IOException {
         int len = getInt8();
+        verifyLength(len);
         byte b[] = new byte[len];
 
         read(b, 0, len);
@@ -199,6 +200,7 @@
 
     public byte[] getBytes16() throws IOException {
         int len = getInt16();
+        verifyLength(len);
         byte b[] = new byte[len];
 
         read(b, 0, len);
@@ -207,10 +209,19 @@
 
     byte[] getBytes24() throws IOException {
         int len = getInt24();
+        verifyLength(len);
         byte b[] = new byte[len];
 
         read(b, 0, len);
         return b;
     }
 
+    // Is a length greater than available bytes in the record?
+    private void verifyLength(int len) throws SSLException {
+        if (len > available()) {
+            throw new SSLException(
+                        "Not enough data to fill declared vector size");
+        }
+    }
+
 }
--- a/src/share/classes/sun/security/ssl/Handshaker.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/ssl/Handshaker.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1079,7 +1079,6 @@
             if (debug != null && Debug.isOn("handshake")) {
                 System.out.println("RSA master secret generation error:");
                 e.printStackTrace(System.out);
-                System.out.println("Generating new random premaster secret");
             }
 
             if (requestedVersion != null) {
@@ -1146,7 +1145,6 @@
             System.out.println("RSA PreMasterSecret version error: expected"
                 + protocolVersion + " or " + requestedVersion + ", decrypted: "
                 + premasterVersion);
-            System.out.println("Generating new random premaster secret");
         }
         preMasterSecret =
             RSAClientKeyExchange.generateDummySecret(requestedVersion);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/HelloExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+
+abstract class HelloExtension {
+
+    final ExtensionType type;
+
+    HelloExtension(ExtensionType type) {
+        this.type = type;
+    }
+
+    // Length of the encoded extension, including the type and length fields
+    abstract int length();
+
+    abstract void send(HandshakeOutStream s) throws IOException;
+
+    public abstract String toString();
+
+}
--- a/src/share/classes/sun/security/ssl/HelloExtensions.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/ssl/HelloExtensions.java	Mon Nov 05 10:33:18 2012 -0500
@@ -153,795 +153,3 @@
         }
     }
 }
-
-final class ExtensionType {
-
-    final int id;
-    final String name;
-
-    private ExtensionType(int id, String name) {
-        this.id = id;
-        this.name = name;
-    }
-
-    public String toString() {
-        return name;
-    }
-
-    static List<ExtensionType> knownExtensions = new ArrayList<>(9);
-
-    static ExtensionType get(int id) {
-        for (ExtensionType ext : knownExtensions) {
-            if (ext.id == id) {
-                return ext;
-            }
-        }
-        return new ExtensionType(id, "type_" + id);
-    }
-
-    private static ExtensionType e(int id, String name) {
-        ExtensionType ext = new ExtensionType(id, name);
-        knownExtensions.add(ext);
-        return ext;
-    }
-
-    // extensions defined in RFC 3546
-    final static ExtensionType EXT_SERVER_NAME =
-            e(0x0000, "server_name");            // IANA registry value: 0
-    final static ExtensionType EXT_MAX_FRAGMENT_LENGTH =
-            e(0x0001, "max_fragment_length");    // IANA registry value: 1
-    final static ExtensionType EXT_CLIENT_CERTIFICATE_URL =
-            e(0x0002, "client_certificate_url"); // IANA registry value: 2
-    final static ExtensionType EXT_TRUSTED_CA_KEYS =
-            e(0x0003, "trusted_ca_keys");        // IANA registry value: 3
-    final static ExtensionType EXT_TRUNCATED_HMAC =
-            e(0x0004, "truncated_hmac");         // IANA registry value: 4
-    final static ExtensionType EXT_STATUS_REQUEST =
-            e(0x0005, "status_request");         // IANA registry value: 5
-
-    // extensions defined in RFC 4681
-    final static ExtensionType EXT_USER_MAPPING =
-            e(0x0006, "user_mapping");           // IANA registry value: 6
-
-    // extensions defined in RFC 5081
-    final static ExtensionType EXT_CERT_TYPE =
-            e(0x0009, "cert_type");              // IANA registry value: 9
-
-    // extensions defined in RFC 4492 (ECC)
-    final static ExtensionType EXT_ELLIPTIC_CURVES =
-            e(0x000A, "elliptic_curves");        // IANA registry value: 10
-    final static ExtensionType EXT_EC_POINT_FORMATS =
-            e(0x000B, "ec_point_formats");       // IANA registry value: 11
-
-    // extensions defined in RFC 5054
-    final static ExtensionType EXT_SRP =
-            e(0x000C, "srp");                    // IANA registry value: 12
-
-    // extensions defined in RFC 5246
-    final static ExtensionType EXT_SIGNATURE_ALGORITHMS =
-            e(0x000D, "signature_algorithms");   // IANA registry value: 13
-
-    // extensions defined in RFC 5746
-    final static ExtensionType EXT_RENEGOTIATION_INFO =
-            e(0xff01, "renegotiation_info");     // IANA registry value: 65281
-}
-
-abstract class HelloExtension {
-
-    final ExtensionType type;
-
-    HelloExtension(ExtensionType type) {
-        this.type = type;
-    }
-
-    // Length of the encoded extension, including the type and length fields
-    abstract int length();
-
-    abstract void send(HandshakeOutStream s) throws IOException;
-
-    public abstract String toString();
-
-}
-
-final class UnknownExtension extends HelloExtension {
-
-    private final byte[] data;
-
-    UnknownExtension(HandshakeInStream s, int len, ExtensionType type)
-            throws IOException {
-        super(type);
-        data = new byte[len];
-        // s.read() does not handle 0-length arrays.
-        if (len != 0) {
-            s.read(data);
-        }
-    }
-
-    int length() {
-        return 4 + data.length;
-    }
-
-    void send(HandshakeOutStream s) throws IOException {
-        s.putInt16(type.id);
-        s.putBytes16(data);
-    }
-
-    public String toString() {
-        return "Unsupported extension " + type + ", data: " +
-            Debug.toString(data);
-    }
-}
-
-/*
- * [RFC 4366/6066] To facilitate secure connections to servers that host
- * multiple 'virtual' servers at a single underlying network address, clients
- * MAY include an extension of type "server_name" in the (extended) client
- * hello.  The "extension_data" field of this extension SHALL contain
- * "ServerNameList" where:
- *
- *     struct {
- *         NameType name_type;
- *         select (name_type) {
- *             case host_name: HostName;
- *         } name;
- *     } ServerName;
- *
- *     enum {
- *         host_name(0), (255)
- *     } NameType;
- *
- *     opaque HostName<1..2^16-1>;
- *
- *     struct {
- *         ServerName server_name_list<1..2^16-1>
- *     } ServerNameList;
- */
-final class ServerNameExtension extends HelloExtension {
-
-    // For backward compatibility, all future data structures associated with
-    // new NameTypes MUST begin with a 16-bit length field.
-    final static int NAME_HEADER_LENGTH = 3;    // NameType: 1 byte
-                                                // Name length: 2 bytes
-    private Map<Integer, SNIServerName> sniMap;
-    private int listLength;     // ServerNameList length
-
-    // constructor for ServerHello
-    ServerNameExtension() throws IOException {
-        super(ExtensionType.EXT_SERVER_NAME);
-
-        listLength = 0;
-        sniMap = Collections.<Integer, SNIServerName>emptyMap();
-    }
-
-    // constructor for ClientHello
-    ServerNameExtension(List<SNIServerName> serverNames)
-            throws IOException {
-        super(ExtensionType.EXT_SERVER_NAME);
-
-        listLength = 0;
-        sniMap = new LinkedHashMap<>();
-        for (SNIServerName serverName : serverNames) {
-            // check for duplicated server name type
-            if (sniMap.put(serverName.getType(), serverName) != null) {
-                // unlikely to happen, but in case ...
-                throw new RuntimeException(
-                    "Duplicated server name of type " + serverName.getType());
-            }
-
-            listLength += serverName.getEncoded().length + NAME_HEADER_LENGTH;
-        }
-
-        // This constructor is used for ClientHello only.  Empty list is
-        // not allowed in client mode.
-        if (listLength == 0) {
-            throw new RuntimeException("The ServerNameList cannot be empty");
-        }
-    }
-
-    // constructor for ServerHello for parsing SNI extension
-    ServerNameExtension(HandshakeInStream s, int len)
-            throws IOException {
-        super(ExtensionType.EXT_SERVER_NAME);
-
-        int remains = len;
-        if (len >= 2) {    // "server_name" extension in ClientHello
-            listLength = s.getInt16();     // ServerNameList length
-            if (listLength == 0 || listLength + 2 != len) {
-                throw new SSLProtocolException(
-                        "Invalid " + type + " extension");
-            }
-
-            remains -= 2;
-            sniMap = new LinkedHashMap<>();
-            while (remains > 0) {
-                int code = s.getInt8();       // NameType
-
-                // HostName (length read in getBytes16);
-                byte[] encoded = s.getBytes16();
-                SNIServerName serverName;
-                switch (code) {
-                    case StandardConstants.SNI_HOST_NAME:
-                        if (encoded.length == 0) {
-                            throw new SSLProtocolException(
-                                "Empty HostName in server name indication");
-                        }
-                        try {
-                            serverName = new SNIHostName(encoded);
-                        } catch (IllegalArgumentException iae) {
-                            SSLProtocolException spe = new SSLProtocolException(
-                                "Illegal server name, type=host_name(" +
-                                code + "), name=" +
-                                (new String(encoded, StandardCharsets.UTF_8)) +
-                                ", value=" + Debug.toString(encoded));
-                            spe.initCause(iae);
-                            throw spe;
-                        }
-                        break;
-                    default:
-                        try {
-                            serverName = new UnknownServerName(code, encoded);
-                        } catch (IllegalArgumentException iae) {
-                            SSLProtocolException spe = new SSLProtocolException(
-                                "Illegal server name, type=(" + code +
-                                "), value=" + Debug.toString(encoded));
-                            spe.initCause(iae);
-                            throw spe;
-                        }
-                }
-                // check for duplicated server name type
-                if (sniMap.put(serverName.getType(), serverName) != null) {
-                    throw new SSLProtocolException(
-                            "Duplicated server name of type " +
-                            serverName.getType());
-                }
-
-                remains -= encoded.length + NAME_HEADER_LENGTH;
-            }
-        } else if (len == 0) {     // "server_name" extension in ServerHello
-            listLength = 0;
-            sniMap = Collections.<Integer, SNIServerName>emptyMap();
-        }
-
-        if (remains != 0) {
-            throw new SSLProtocolException("Invalid server_name extension");
-        }
-    }
-
-    List<SNIServerName> getServerNames() {
-        if (sniMap != null && !sniMap.isEmpty()) {
-            return Collections.<SNIServerName>unmodifiableList(
-                                        new ArrayList<>(sniMap.values()));
-        }
-
-        return Collections.<SNIServerName>emptyList();
-    }
-
-    /*
-     * Is the extension recognized by the corresponding matcher?
-     *
-     * This method is used to check whether the server name indication can
-     * be recognized by the server name matchers.
-     *
-     * Per RFC 6066, if the server understood the ClientHello extension but
-     * does not recognize the server name, the server SHOULD take one of two
-     * actions: either abort the handshake by sending a fatal-level
-     * unrecognized_name(112) alert or continue the handshake.
-     *
-     * If there is an instance of SNIMatcher defined for a particular name
-     * type, it must be used to perform match operations on the server name.
-     */
-    boolean isMatched(Collection<SNIMatcher> matchers) {
-        if (sniMap != null && !sniMap.isEmpty()) {
-            for (SNIMatcher matcher : matchers) {
-                SNIServerName sniName = sniMap.get(matcher.getType());
-                if (sniName != null && (!matcher.matches(sniName))) {
-                    return false;
-                }
-            }
-        }
-
-        return true;
-    }
-
-    /*
-     * Is the extension is identical to a server name list?
-     *
-     * This method is used to check the server name indication during session
-     * resumption.
-     *
-     * Per RFC 6066, when the server is deciding whether or not to accept a
-     * request to resume a session, the contents of a server_name extension
-     * MAY be used in the lookup of the session in the session cache.  The
-     * client SHOULD include the same server_name extension in the session
-     * resumption request as it did in the full handshake that established
-     * the session.  A server that implements this extension MUST NOT accept
-     * the request to resume the session if the server_name extension contains
-     * a different name.  Instead, it proceeds with a full handshake to
-     * establish a new session.  When resuming a session, the server MUST NOT
-     * include a server_name extension in the server hello.
-     */
-    boolean isIdentical(List<SNIServerName> other) {
-        if (other.size() == sniMap.size()) {
-            for(SNIServerName sniInOther : other) {
-                SNIServerName sniName = sniMap.get(sniInOther.getType());
-                if (sniName == null || !sniInOther.equals(sniName)) {
-                    return false;
-                }
-            }
-
-            return true;
-        }
-
-        return false;
-    }
-
-    int length() {
-        return listLength == 0 ? 4 : 6 + listLength;
-    }
-
-    void send(HandshakeOutStream s) throws IOException {
-        s.putInt16(type.id);
-        if (listLength == 0) {
-            s.putInt16(listLength);     // in ServerHello, empty extension_data
-        } else {
-            s.putInt16(listLength + 2); // length of extension_data
-            s.putInt16(listLength);     // length of ServerNameList
-
-            for (SNIServerName sniName : sniMap.values()) {
-                s.putInt8(sniName.getType());         // server name type
-                s.putBytes16(sniName.getEncoded());   // server name value
-            }
-        }
-    }
-
-    public String toString() {
-        StringBuffer buffer = new StringBuffer();
-        for (SNIServerName sniName : sniMap.values()) {
-            buffer.append("[" + sniName + "]");
-        }
-
-        return "Extension " + type + ", server_name: " + buffer;
-    }
-
-    private static class UnknownServerName extends SNIServerName {
-        UnknownServerName(int code, byte[] encoded) {
-            super(code, encoded);
-        }
-    }
-
-}
-
-final class SupportedEllipticCurvesExtension extends HelloExtension {
-
-    // the extension value to send in the ClientHello message
-    static final SupportedEllipticCurvesExtension DEFAULT;
-
-    private static final boolean fips;
-
-    static {
-        int[] ids;
-        fips = SunJSSE.isFIPS();
-        if (fips == false) {
-            ids = new int[] {
-                // NIST curves first
-                // prefer NIST P-256, rest in order of increasing key length
-                23, 1, 3, 19, 21, 6, 7, 9, 10, 24, 11, 12, 25, 13, 14,
-                // non-NIST curves
-                15, 16, 17, 2, 18, 4, 5, 20, 8, 22,
-            };
-        } else {
-            ids = new int[] {
-                // same as above, but allow only NIST curves in FIPS mode
-                23, 1, 3, 19, 21, 6, 7, 9, 10, 24, 11, 12, 25, 13, 14,
-            };
-        }
-        DEFAULT = new SupportedEllipticCurvesExtension(ids);
-    }
-
-    private final int[] curveIds;
-
-    private SupportedEllipticCurvesExtension(int[] curveIds) {
-        super(ExtensionType.EXT_ELLIPTIC_CURVES);
-        this.curveIds = curveIds;
-    }
-
-    SupportedEllipticCurvesExtension(HandshakeInStream s, int len)
-            throws IOException {
-        super(ExtensionType.EXT_ELLIPTIC_CURVES);
-        int k = s.getInt16();
-        if (((len & 1) != 0) || (k + 2 != len)) {
-            throw new SSLProtocolException("Invalid " + type + " extension");
-        }
-        curveIds = new int[k >> 1];
-        for (int i = 0; i < curveIds.length; i++) {
-            curveIds[i] = s.getInt16();
-        }
-    }
-
-    boolean contains(int index) {
-        for (int curveId : curveIds) {
-            if (index == curveId) {
-                return true;
-            }
-        }
-        return false;
-    }
-
-    // Return a reference to the internal curveIds array.
-    // The caller must NOT modify the contents.
-    int[] curveIds() {
-        return curveIds;
-    }
-
-    int length() {
-        return 6 + (curveIds.length << 1);
-    }
-
-    void send(HandshakeOutStream s) throws IOException {
-        s.putInt16(type.id);
-        int k = curveIds.length << 1;
-        s.putInt16(k + 2);
-        s.putInt16(k);
-        for (int curveId : curveIds) {
-            s.putInt16(curveId);
-        }
-    }
-
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append("Extension " + type + ", curve names: {");
-        boolean first = true;
-        for (int curveId : curveIds) {
-            if (first) {
-                first = false;
-            } else {
-                sb.append(", ");
-            }
-            // first check if it is a known named curve, then try other cases.
-            String oid = getCurveOid(curveId);
-            if (oid != null) {
-                ECParameterSpec spec = JsseJce.getECParameterSpec(oid);
-                // this toString() output will look nice for the current
-                // implementation of the ECParameterSpec class in the Sun
-                // provider, but may not look good for other implementations.
-                if (spec != null) {
-                    sb.append(spec.toString().split(" ")[0]);
-                } else {
-                    sb.append(oid);
-                }
-            } else if (curveId == ARBITRARY_PRIME) {
-                sb.append("arbitrary_explicit_prime_curves");
-            } else if (curveId == ARBITRARY_CHAR2) {
-                sb.append("arbitrary_explicit_char2_curves");
-            } else {
-                sb.append("unknown curve " + curveId);
-            }
-        }
-        sb.append("}");
-        return sb.toString();
-    }
-
-    // Test whether we support the curve with the given index.
-    static boolean isSupported(int index) {
-        if ((index <= 0) || (index >= NAMED_CURVE_OID_TABLE.length)) {
-            return false;
-        }
-        if (fips == false) {
-            // in non-FIPS mode, we support all valid indices
-            return true;
-        }
-        return DEFAULT.contains(index);
-    }
-
-    static int getCurveIndex(ECParameterSpec params) {
-        String oid = JsseJce.getNamedCurveOid(params);
-        if (oid == null) {
-            return -1;
-        }
-        Integer n = curveIndices.get(oid);
-        return (n == null) ? -1 : n;
-    }
-
-    static String getCurveOid(int index) {
-        if ((index > 0) && (index < NAMED_CURVE_OID_TABLE.length)) {
-            return NAMED_CURVE_OID_TABLE[index];
-        }
-        return null;
-    }
-
-    private final static int ARBITRARY_PRIME = 0xff01;
-    private final static int ARBITRARY_CHAR2 = 0xff02;
-
-    // See sun.security.ec.NamedCurve for the OIDs
-    private final static String[] NAMED_CURVE_OID_TABLE = new String[] {
-        null,                   //  (0) unused
-        "1.3.132.0.1",          //  (1) sect163k1, NIST K-163
-        "1.3.132.0.2",          //  (2) sect163r1
-        "1.3.132.0.15",         //  (3) sect163r2, NIST B-163
-        "1.3.132.0.24",         //  (4) sect193r1
-        "1.3.132.0.25",         //  (5) sect193r2
-        "1.3.132.0.26",         //  (6) sect233k1, NIST K-233
-        "1.3.132.0.27",         //  (7) sect233r1, NIST B-233
-        "1.3.132.0.3",          //  (8) sect239k1
-        "1.3.132.0.16",         //  (9) sect283k1, NIST K-283
-        "1.3.132.0.17",         // (10) sect283r1, NIST B-283
-        "1.3.132.0.36",         // (11) sect409k1, NIST K-409
-        "1.3.132.0.37",         // (12) sect409r1, NIST B-409
-        "1.3.132.0.38",         // (13) sect571k1, NIST K-571
-        "1.3.132.0.39",         // (14) sect571r1, NIST B-571
-        "1.3.132.0.9",          // (15) secp160k1
-        "1.3.132.0.8",          // (16) secp160r1
-        "1.3.132.0.30",         // (17) secp160r2
-        "1.3.132.0.31",         // (18) secp192k1
-        "1.2.840.10045.3.1.1",  // (19) secp192r1, NIST P-192
-        "1.3.132.0.32",         // (20) secp224k1
-        "1.3.132.0.33",         // (21) secp224r1, NIST P-224
-        "1.3.132.0.10",         // (22) secp256k1
-        "1.2.840.10045.3.1.7",  // (23) secp256r1, NIST P-256
-        "1.3.132.0.34",         // (24) secp384r1, NIST P-384
-        "1.3.132.0.35",         // (25) secp521r1, NIST P-521
-    };
-
-    private final static Map<String,Integer> curveIndices;
-
-    static {
-        curveIndices = new HashMap<String,Integer>();
-        for (int i = 1; i < NAMED_CURVE_OID_TABLE.length; i++) {
-            curveIndices.put(NAMED_CURVE_OID_TABLE[i], i);
-        }
-    }
-
-}
-
-final class SupportedEllipticPointFormatsExtension extends HelloExtension {
-
-    final static int FMT_UNCOMPRESSED = 0;
-    final static int FMT_ANSIX962_COMPRESSED_PRIME = 1;
-    final static int FMT_ANSIX962_COMPRESSED_CHAR2 = 2;
-
-    static final HelloExtension DEFAULT =
-        new SupportedEllipticPointFormatsExtension(
-            new byte[] {FMT_UNCOMPRESSED});
-
-    private final byte[] formats;
-
-    private SupportedEllipticPointFormatsExtension(byte[] formats) {
-        super(ExtensionType.EXT_EC_POINT_FORMATS);
-        this.formats = formats;
-    }
-
-    SupportedEllipticPointFormatsExtension(HandshakeInStream s, int len)
-            throws IOException {
-        super(ExtensionType.EXT_EC_POINT_FORMATS);
-        formats = s.getBytes8();
-        // RFC 4492 says uncompressed points must always be supported.
-        // Check just to make sure.
-        boolean uncompressed = false;
-        for (int format : formats) {
-            if (format == FMT_UNCOMPRESSED) {
-                uncompressed = true;
-                break;
-            }
-        }
-        if (uncompressed == false) {
-            throw new SSLProtocolException
-                ("Peer does not support uncompressed points");
-        }
-    }
-
-    int length() {
-        return 5 + formats.length;
-    }
-
-    void send(HandshakeOutStream s) throws IOException {
-        s.putInt16(type.id);
-        s.putInt16(formats.length + 1);
-        s.putBytes8(formats);
-    }
-
-    private static String toString(byte format) {
-        int f = format & 0xff;
-        switch (f) {
-        case FMT_UNCOMPRESSED:
-            return "uncompressed";
-        case FMT_ANSIX962_COMPRESSED_PRIME:
-            return "ansiX962_compressed_prime";
-        case FMT_ANSIX962_COMPRESSED_CHAR2:
-            return "ansiX962_compressed_char2";
-        default:
-            return "unknown-" + f;
-        }
-    }
-
-    public String toString() {
-        List<String> list = new ArrayList<>();
-        for (byte format : formats) {
-            list.add(toString(format));
-        }
-        return "Extension " + type + ", formats: " + list;
-    }
-}
-
-/*
- * For secure renegotiation, RFC5746 defines a new TLS extension,
- * "renegotiation_info" (with extension type 0xff01), which contains a
- * cryptographic binding to the enclosing TLS connection (if any) for
- * which the renegotiation is being performed.  The "extension data"
- * field of this extension contains a "RenegotiationInfo" structure:
- *
- *      struct {
- *          opaque renegotiated_connection<0..255>;
- *      } RenegotiationInfo;
- */
-final class RenegotiationInfoExtension extends HelloExtension {
-    private final byte[] renegotiated_connection;
-
-    RenegotiationInfoExtension(byte[] clientVerifyData,
-                byte[] serverVerifyData) {
-        super(ExtensionType.EXT_RENEGOTIATION_INFO);
-
-        if (clientVerifyData.length != 0) {
-            renegotiated_connection =
-                    new byte[clientVerifyData.length + serverVerifyData.length];
-            System.arraycopy(clientVerifyData, 0, renegotiated_connection,
-                    0, clientVerifyData.length);
-
-            if (serverVerifyData.length != 0) {
-                System.arraycopy(serverVerifyData, 0, renegotiated_connection,
-                        clientVerifyData.length, serverVerifyData.length);
-            }
-        } else {
-            // ignore both the client and server verify data.
-            renegotiated_connection = new byte[0];
-        }
-    }
-
-    RenegotiationInfoExtension(HandshakeInStream s, int len)
-                throws IOException {
-        super(ExtensionType.EXT_RENEGOTIATION_INFO);
-
-        // check the extension length
-        if (len < 1) {
-            throw new SSLProtocolException("Invalid " + type + " extension");
-        }
-
-        int renegoInfoDataLen = s.getInt8();
-        if (renegoInfoDataLen + 1 != len) {  // + 1 = the byte we just read
-            throw new SSLProtocolException("Invalid " + type + " extension");
-        }
-
-        renegotiated_connection = new byte[renegoInfoDataLen];
-        if (renegoInfoDataLen != 0) {
-            s.read(renegotiated_connection, 0, renegoInfoDataLen);
-        }
-    }
-
-
-    // Length of the encoded extension, including the type and length fields
-    int length() {
-        return 5 + renegotiated_connection.length;
-    }
-
-    void send(HandshakeOutStream s) throws IOException {
-        s.putInt16(type.id);
-        s.putInt16(renegotiated_connection.length + 1);
-        s.putBytes8(renegotiated_connection);
-    }
-
-    boolean isEmpty() {
-        return renegotiated_connection.length == 0;
-    }
-
-    byte[] getRenegotiatedConnection() {
-        return renegotiated_connection;
-    }
-
-    public String toString() {
-        return "Extension " + type + ", renegotiated_connection: " +
-                    (renegotiated_connection.length == 0 ? "<empty>" :
-                    Debug.toString(renegotiated_connection));
-    }
-
-}
-
-/*
- * [RFC5246] The client uses the "signature_algorithms" extension to
- * indicate to the server which signature/hash algorithm pairs may be
- * used in digital signatures.  The "extension_data" field of this
- * extension contains a "supported_signature_algorithms" value.
- *
- *     enum {
- *         none(0), md5(1), sha1(2), sha224(3), sha256(4), sha384(5),
- *         sha512(6), (255)
- *     } HashAlgorithm;
- *
- *     enum { anonymous(0), rsa(1), dsa(2), ecdsa(3), (255) }
- *       SignatureAlgorithm;
- *
- *     struct {
- *           HashAlgorithm hash;
- *           SignatureAlgorithm signature;
- *     } SignatureAndHashAlgorithm;
- *
- *     SignatureAndHashAlgorithm
- *       supported_signature_algorithms<2..2^16-2>;
- */
-final class SignatureAlgorithmsExtension extends HelloExtension {
-
-    private Collection<SignatureAndHashAlgorithm> algorithms;
-    private int algorithmsLen;  // length of supported_signature_algorithms
-
-    SignatureAlgorithmsExtension(
-            Collection<SignatureAndHashAlgorithm> signAlgs) {
-
-        super(ExtensionType.EXT_SIGNATURE_ALGORITHMS);
-
-        algorithms = new ArrayList<SignatureAndHashAlgorithm>(signAlgs);
-        algorithmsLen =
-            SignatureAndHashAlgorithm.sizeInRecord() * algorithms.size();
-    }
-
-    SignatureAlgorithmsExtension(HandshakeInStream s, int len)
-                throws IOException {
-        super(ExtensionType.EXT_SIGNATURE_ALGORITHMS);
-
-        algorithmsLen = s.getInt16();
-        if (algorithmsLen == 0 || algorithmsLen + 2 != len) {
-            throw new SSLProtocolException("Invalid " + type + " extension");
-        }
-
-        algorithms = new ArrayList<SignatureAndHashAlgorithm>();
-        int remains = algorithmsLen;
-        int sequence = 0;
-        while (remains > 1) {   // needs at least two bytes
-            int hash = s.getInt8();         // hash algorithm
-            int signature = s.getInt8();    // signature algorithm
-
-            SignatureAndHashAlgorithm algorithm =
-                SignatureAndHashAlgorithm.valueOf(hash, signature, ++sequence);
-            algorithms.add(algorithm);
-            remains -= 2;  // one byte for hash, one byte for signature
-        }
-
-        if (remains != 0) {
-            throw new SSLProtocolException("Invalid server_name extension");
-        }
-    }
-
-    Collection<SignatureAndHashAlgorithm> getSignAlgorithms() {
-        return algorithms;
-    }
-
-    @Override
-    int length() {
-        return 6 + algorithmsLen;
-    }
-
-    @Override
-    void send(HandshakeOutStream s) throws IOException {
-        s.putInt16(type.id);
-        s.putInt16(algorithmsLen + 2);
-        s.putInt16(algorithmsLen);
-
-        for (SignatureAndHashAlgorithm algorithm : algorithms) {
-            s.putInt8(algorithm.getHashValue());      // HashAlgorithm
-            s.putInt8(algorithm.getSignatureValue()); // SignatureAlgorithm
-        }
-    }
-
-    @Override
-    public String toString() {
-        StringBuffer buffer = new StringBuffer();
-        boolean opened = false;
-        for (SignatureAndHashAlgorithm signAlg : algorithms) {
-            if (opened) {
-                buffer.append(", " + signAlg.getAlgorithmName());
-            } else {
-                buffer.append(signAlg.getAlgorithmName());
-                opened = true;
-            }
-        }
-
-        return "Extension " + type + ", signature_algorithms: " + buffer;
-    }
-}
--- a/src/share/classes/sun/security/ssl/RSAClientKeyExchange.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/security/ssl/RSAClientKeyExchange.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1996, 2010, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1996, 2012, 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
@@ -36,6 +36,7 @@
 import javax.net.ssl.*;
 
 import sun.security.internal.spec.TlsRsaPremasterSecretParameterSpec;
+import sun.security.util.KeyLength;
 
 /**
  * This is the client key exchange message (CLIENT --> SERVER) used with
@@ -192,26 +193,38 @@
                         "unable to get the plaintext of the premaster secret");
                 }
 
-                // We are not always able to get the encoded key of the
-                // premaster secret. Pass the cheking to master secret
+                int keySize = KeyLength.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);
+                }
+
+                // 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]) {
+
                     return secretKey;
-                } else if (clientHelloVersion.v <= ProtocolVersion.TLS10.v) {
+                } else if (clientHelloVersion.v <= ProtocolVersion.TLS10.v &&
+                           currentVersion.major == encoded[0] &&
+                           currentVersion.minor == encoded[1]) {
                     /*
-                     * we never checked the client_version in server side
-                     * for TLS v1.0 and SSL v3.0. For compatibility, we
-                     * maintain this behavior.
+                     * 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.
                      */
-                    if (currentVersion.major == encoded[0] &&
-                        currentVersion.minor == encoded[1]) {
-                        this.protocolVersion = currentVersion;
-                        return secretKey;
-                    }
+                    this.protocolVersion = currentVersion;
+                    return secretKey;
                 }
 
                 if (debug != null && Debug.isOn("handshake")) {
@@ -220,22 +233,23 @@
                         ", 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);
                 }
+
+                return generateDummySecret(clientHelloVersion);
             }
         }
 
-        if (debug != null && Debug.isOn("handshake")) {
-            if (failoverException != null) {
-                System.out.println("Error decrypting premaster secret:");
-                failoverException.printStackTrace(System.out);
-            }
-
-            System.out.println("Generating random secret");
+        if (debug != null && Debug.isOn("handshake") &&
+                        failoverException != null) {
+            System.out.println("Error decrypting premaster secret:");
+            failoverException.printStackTrace(System.out);
         }
 
         return generateDummySecret(clientHelloVersion);
@@ -243,6 +257,10 @@
 
     // generate a premaster secret with the specified version number
     static SecretKey generateDummySecret(ProtocolVersion version) {
+        if (debug != null && Debug.isOn("handshake")) {
+            System.out.println("Generating a random fake premaster secret");
+        }
+
         try {
             String s = ((version.v >= ProtocolVersion.TLS12.v) ?
                 "SunTls12RsaPremasterSecret" : "SunTlsRsaPremasterSecret");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/RenegotiationInfoExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,112 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+
+import javax.net.ssl.SSLProtocolException;
+
+/*
+ * For secure renegotiation, RFC5746 defines a new TLS extension,
+ * "renegotiation_info" (with extension type 0xff01), which contains a
+ * cryptographic binding to the enclosing TLS connection (if any) for
+ * which the renegotiation is being performed.  The "extension data"
+ * field of this extension contains a "RenegotiationInfo" structure:
+ *
+ *      struct {
+ *          opaque renegotiated_connection<0..255>;
+ *      } RenegotiationInfo;
+ */
+final class RenegotiationInfoExtension extends HelloExtension {
+    private final byte[] renegotiated_connection;
+
+    RenegotiationInfoExtension(byte[] clientVerifyData,
+                byte[] serverVerifyData) {
+        super(ExtensionType.EXT_RENEGOTIATION_INFO);
+
+        if (clientVerifyData.length != 0) {
+            renegotiated_connection =
+                    new byte[clientVerifyData.length + serverVerifyData.length];
+            System.arraycopy(clientVerifyData, 0, renegotiated_connection,
+                    0, clientVerifyData.length);
+
+            if (serverVerifyData.length != 0) {
+                System.arraycopy(serverVerifyData, 0, renegotiated_connection,
+                        clientVerifyData.length, serverVerifyData.length);
+            }
+        } else {
+            // ignore both the client and server verify data.
+            renegotiated_connection = new byte[0];
+        }
+    }
+
+    RenegotiationInfoExtension(HandshakeInStream s, int len)
+                throws IOException {
+        super(ExtensionType.EXT_RENEGOTIATION_INFO);
+
+        // check the extension length
+        if (len < 1) {
+            throw new SSLProtocolException("Invalid " + type + " extension");
+        }
+
+        int renegoInfoDataLen = s.getInt8();
+        if (renegoInfoDataLen + 1 != len) {  // + 1 = the byte we just read
+            throw new SSLProtocolException("Invalid " + type + " extension");
+        }
+
+        renegotiated_connection = new byte[renegoInfoDataLen];
+        if (renegoInfoDataLen != 0) {
+            s.read(renegotiated_connection, 0, renegoInfoDataLen);
+        }
+    }
+
+
+    // Length of the encoded extension, including the type and length fields
+    int length() {
+        return 5 + renegotiated_connection.length;
+    }
+
+    void send(HandshakeOutStream s) throws IOException {
+        s.putInt16(type.id);
+        s.putInt16(renegotiated_connection.length + 1);
+        s.putBytes8(renegotiated_connection);
+    }
+
+    boolean isEmpty() {
+        return renegotiated_connection.length == 0;
+    }
+
+    byte[] getRenegotiatedConnection() {
+        return renegotiated_connection;
+    }
+
+    public String toString() {
+        return "Extension " + type + ", renegotiated_connection: " +
+                    (renegotiated_connection.length == 0 ? "<empty>" :
+                    Debug.toString(renegotiated_connection));
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/ServerNameExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,280 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+import java.nio.charset.StandardCharsets;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.List;
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+import javax.net.ssl.SNIHostName;
+import javax.net.ssl.SNIMatcher;
+import javax.net.ssl.SNIServerName;
+import javax.net.ssl.SSLProtocolException;
+import javax.net.ssl.StandardConstants;
+
+/*
+ * [RFC 4366/6066] To facilitate secure connections to servers that host
+ * multiple 'virtual' servers at a single underlying network address, clients
+ * MAY include an extension of type "server_name" in the (extended) client
+ * hello.  The "extension_data" field of this extension SHALL contain
+ * "ServerNameList" where:
+ *
+ *     struct {
+ *         NameType name_type;
+ *         select (name_type) {
+ *             case host_name: HostName;
+ *         } name;
+ *     } ServerName;
+ *
+ *     enum {
+ *         host_name(0), (255)
+ *     } NameType;
+ *
+ *     opaque HostName<1..2^16-1>;
+ *
+ *     struct {
+ *         ServerName server_name_list<1..2^16-1>
+ *     } ServerNameList;
+ */
+final class ServerNameExtension extends HelloExtension {
+
+    // For backward compatibility, all future data structures associated with
+    // new NameTypes MUST begin with a 16-bit length field.
+    final static int NAME_HEADER_LENGTH = 3;    // NameType: 1 byte
+                                                // Name length: 2 bytes
+    private Map<Integer, SNIServerName> sniMap;
+    private int listLength;     // ServerNameList length
+
+    // constructor for ServerHello
+    ServerNameExtension() throws IOException {
+        super(ExtensionType.EXT_SERVER_NAME);
+
+        listLength = 0;
+        sniMap = Collections.<Integer, SNIServerName>emptyMap();
+    }
+
+    // constructor for ClientHello
+    ServerNameExtension(List<SNIServerName> serverNames)
+            throws IOException {
+        super(ExtensionType.EXT_SERVER_NAME);
+
+        listLength = 0;
+        sniMap = new LinkedHashMap<>();
+        for (SNIServerName serverName : serverNames) {
+            // check for duplicated server name type
+            if (sniMap.put(serverName.getType(), serverName) != null) {
+                // unlikely to happen, but in case ...
+                throw new RuntimeException(
+                    "Duplicated server name of type " + serverName.getType());
+            }
+
+            listLength += serverName.getEncoded().length + NAME_HEADER_LENGTH;
+        }
+
+        // This constructor is used for ClientHello only.  Empty list is
+        // not allowed in client mode.
+        if (listLength == 0) {
+            throw new RuntimeException("The ServerNameList cannot be empty");
+        }
+    }
+
+    // constructor for ServerHello for parsing SNI extension
+    ServerNameExtension(HandshakeInStream s, int len)
+            throws IOException {
+        super(ExtensionType.EXT_SERVER_NAME);
+
+        int remains = len;
+        if (len >= 2) {    // "server_name" extension in ClientHello
+            listLength = s.getInt16();     // ServerNameList length
+            if (listLength == 0 || listLength + 2 != len) {
+                throw new SSLProtocolException(
+                        "Invalid " + type + " extension");
+            }
+
+            remains -= 2;
+            sniMap = new LinkedHashMap<>();
+            while (remains > 0) {
+                int code = s.getInt8();       // NameType
+
+                // HostName (length read in getBytes16);
+                byte[] encoded = s.getBytes16();
+                SNIServerName serverName;
+                switch (code) {
+                    case StandardConstants.SNI_HOST_NAME:
+                        if (encoded.length == 0) {
+                            throw new SSLProtocolException(
+                                "Empty HostName in server name indication");
+                        }
+                        try {
+                            serverName = new SNIHostName(encoded);
+                        } catch (IllegalArgumentException iae) {
+                            SSLProtocolException spe = new SSLProtocolException(
+                                "Illegal server name, type=host_name(" +
+                                code + "), name=" +
+                                (new String(encoded, StandardCharsets.UTF_8)) +
+                                ", value=" + Debug.toString(encoded));
+                            spe.initCause(iae);
+                            throw spe;
+                        }
+                        break;
+                    default:
+                        try {
+                            serverName = new UnknownServerName(code, encoded);
+                        } catch (IllegalArgumentException iae) {
+                            SSLProtocolException spe = new SSLProtocolException(
+                                "Illegal server name, type=(" + code +
+                                "), value=" + Debug.toString(encoded));
+                            spe.initCause(iae);
+                            throw spe;
+                        }
+                }
+                // check for duplicated server name type
+                if (sniMap.put(serverName.getType(), serverName) != null) {
+                    throw new SSLProtocolException(
+                            "Duplicated server name of type " +
+                            serverName.getType());
+                }
+
+                remains -= encoded.length + NAME_HEADER_LENGTH;
+            }
+        } else if (len == 0) {     // "server_name" extension in ServerHello
+            listLength = 0;
+            sniMap = Collections.<Integer, SNIServerName>emptyMap();
+        }
+
+        if (remains != 0) {
+            throw new SSLProtocolException("Invalid server_name extension");
+        }
+    }
+
+    List<SNIServerName> getServerNames() {
+        if (sniMap != null && !sniMap.isEmpty()) {
+            return Collections.<SNIServerName>unmodifiableList(
+                                        new ArrayList<>(sniMap.values()));
+        }
+
+        return Collections.<SNIServerName>emptyList();
+    }
+
+    /*
+     * Is the extension recognized by the corresponding matcher?
+     *
+     * This method is used to check whether the server name indication can
+     * be recognized by the server name matchers.
+     *
+     * Per RFC 6066, if the server understood the ClientHello extension but
+     * does not recognize the server name, the server SHOULD take one of two
+     * actions: either abort the handshake by sending a fatal-level
+     * unrecognized_name(112) alert or continue the handshake.
+     *
+     * If there is an instance of SNIMatcher defined for a particular name
+     * type, it must be used to perform match operations on the server name.
+     */
+    boolean isMatched(Collection<SNIMatcher> matchers) {
+        if (sniMap != null && !sniMap.isEmpty()) {
+            for (SNIMatcher matcher : matchers) {
+                SNIServerName sniName = sniMap.get(matcher.getType());
+                if (sniName != null && (!matcher.matches(sniName))) {
+                    return false;
+                }
+            }
+        }
+
+        return true;
+    }
+
+    /*
+     * Is the extension is identical to a server name list?
+     *
+     * This method is used to check the server name indication during session
+     * resumption.
+     *
+     * Per RFC 6066, when the server is deciding whether or not to accept a
+     * request to resume a session, the contents of a server_name extension
+     * MAY be used in the lookup of the session in the session cache.  The
+     * client SHOULD include the same server_name extension in the session
+     * resumption request as it did in the full handshake that established
+     * the session.  A server that implements this extension MUST NOT accept
+     * the request to resume the session if the server_name extension contains
+     * a different name.  Instead, it proceeds with a full handshake to
+     * establish a new session.  When resuming a session, the server MUST NOT
+     * include a server_name extension in the server hello.
+     */
+    boolean isIdentical(List<SNIServerName> other) {
+        if (other.size() == sniMap.size()) {
+            for(SNIServerName sniInOther : other) {
+                SNIServerName sniName = sniMap.get(sniInOther.getType());
+                if (sniName == null || !sniInOther.equals(sniName)) {
+                    return false;
+                }
+            }
+
+            return true;
+        }
+
+        return false;
+    }
+
+    int length() {
+        return listLength == 0 ? 4 : 6 + listLength;
+    }
+
+    void send(HandshakeOutStream s) throws IOException {
+        s.putInt16(type.id);
+        if (listLength == 0) {
+            s.putInt16(listLength);     // in ServerHello, empty extension_data
+        } else {
+            s.putInt16(listLength + 2); // length of extension_data
+            s.putInt16(listLength);     // length of ServerNameList
+
+            for (SNIServerName sniName : sniMap.values()) {
+                s.putInt8(sniName.getType());         // server name type
+                s.putBytes16(sniName.getEncoded());   // server name value
+            }
+        }
+    }
+
+    public String toString() {
+        StringBuffer buffer = new StringBuffer();
+        for (SNIServerName sniName : sniMap.values()) {
+            buffer.append("[" + sniName + "]");
+        }
+
+        return "Extension " + type + ", server_name: " + buffer;
+    }
+
+    private static class UnknownServerName extends SNIServerName {
+        UnknownServerName(int code, byte[] encoded) {
+            super(code, encoded);
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/SignatureAlgorithmsExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,135 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Collection;
+
+import javax.net.ssl.SSLProtocolException;
+
+/*
+ * [RFC5246] The client uses the "signature_algorithms" extension to
+ * indicate to the server which signature/hash algorithm pairs may be
+ * used in digital signatures.  The "extension_data" field of this
+ * extension contains a "supported_signature_algorithms" value.
+ *
+ *     enum {
+ *         none(0), md5(1), sha1(2), sha224(3), sha256(4), sha384(5),
+ *         sha512(6), (255)
+ *     } HashAlgorithm;
+ *
+ *     enum { anonymous(0), rsa(1), dsa(2), ecdsa(3), (255) }
+ *       SignatureAlgorithm;
+ *
+ *     struct {
+ *           HashAlgorithm hash;
+ *           SignatureAlgorithm signature;
+ *     } SignatureAndHashAlgorithm;
+ *
+ *     SignatureAndHashAlgorithm
+ *       supported_signature_algorithms<2..2^16-2>;
+ */
+final class SignatureAlgorithmsExtension extends HelloExtension {
+
+    private Collection<SignatureAndHashAlgorithm> algorithms;
+    private int algorithmsLen;  // length of supported_signature_algorithms
+
+    SignatureAlgorithmsExtension(
+            Collection<SignatureAndHashAlgorithm> signAlgs) {
+
+        super(ExtensionType.EXT_SIGNATURE_ALGORITHMS);
+
+        algorithms = new ArrayList<SignatureAndHashAlgorithm>(signAlgs);
+        algorithmsLen =
+            SignatureAndHashAlgorithm.sizeInRecord() * algorithms.size();
+    }
+
+    SignatureAlgorithmsExtension(HandshakeInStream s, int len)
+                throws IOException {
+        super(ExtensionType.EXT_SIGNATURE_ALGORITHMS);
+
+        algorithmsLen = s.getInt16();
+        if (algorithmsLen == 0 || algorithmsLen + 2 != len) {
+            throw new SSLProtocolException("Invalid " + type + " extension");
+        }
+
+        algorithms = new ArrayList<SignatureAndHashAlgorithm>();
+        int remains = algorithmsLen;
+        int sequence = 0;
+        while (remains > 1) {   // needs at least two bytes
+            int hash = s.getInt8();         // hash algorithm
+            int signature = s.getInt8();    // signature algorithm
+
+            SignatureAndHashAlgorithm algorithm =
+                SignatureAndHashAlgorithm.valueOf(hash, signature, ++sequence);
+            algorithms.add(algorithm);
+            remains -= 2;  // one byte for hash, one byte for signature
+        }
+
+        if (remains != 0) {
+            throw new SSLProtocolException("Invalid server_name extension");
+        }
+    }
+
+    Collection<SignatureAndHashAlgorithm> getSignAlgorithms() {
+        return algorithms;
+    }
+
+    @Override
+    int length() {
+        return 6 + algorithmsLen;
+    }
+
+    @Override
+    void send(HandshakeOutStream s) throws IOException {
+        s.putInt16(type.id);
+        s.putInt16(algorithmsLen + 2);
+        s.putInt16(algorithmsLen);
+
+        for (SignatureAndHashAlgorithm algorithm : algorithms) {
+            s.putInt8(algorithm.getHashValue());      // HashAlgorithm
+            s.putInt8(algorithm.getSignatureValue()); // SignatureAlgorithm
+        }
+    }
+
+    @Override
+    public String toString() {
+        StringBuffer buffer = new StringBuffer();
+        boolean opened = false;
+        for (SignatureAndHashAlgorithm signAlg : algorithms) {
+            if (opened) {
+                buffer.append(", " + signAlg.getAlgorithmName());
+            } else {
+                buffer.append(signAlg.getAlgorithmName());
+                opened = true;
+            }
+        }
+
+        return "Extension " + type + ", signature_algorithms: " + buffer;
+    }
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/SupportedEllipticCurvesExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,215 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+import java.security.spec.ECParameterSpec;
+import java.util.HashMap;
+import java.util.Map;
+
+import javax.net.ssl.SSLProtocolException;
+
+final class SupportedEllipticCurvesExtension extends HelloExtension {
+
+    // the extension value to send in the ClientHello message
+    static final SupportedEllipticCurvesExtension DEFAULT;
+
+    private static final boolean fips;
+
+    static {
+        int[] ids;
+        fips = SunJSSE.isFIPS();
+        if (fips == false) {
+            ids = new int[] {
+                // NIST curves first
+                // prefer NIST P-256, rest in order of increasing key length
+                23, 1, 3, 19, 21, 6, 7, 9, 10, 24, 11, 12, 25, 13, 14,
+                // non-NIST curves
+                15, 16, 17, 2, 18, 4, 5, 20, 8, 22,
+            };
+        } else {
+            ids = new int[] {
+                // same as above, but allow only NIST curves in FIPS mode
+                23, 1, 3, 19, 21, 6, 7, 9, 10, 24, 11, 12, 25, 13, 14,
+            };
+        }
+        DEFAULT = new SupportedEllipticCurvesExtension(ids);
+    }
+
+    private final int[] curveIds;
+
+    private SupportedEllipticCurvesExtension(int[] curveIds) {
+        super(ExtensionType.EXT_ELLIPTIC_CURVES);
+        this.curveIds = curveIds;
+    }
+
+    SupportedEllipticCurvesExtension(HandshakeInStream s, int len)
+            throws IOException {
+        super(ExtensionType.EXT_ELLIPTIC_CURVES);
+        int k = s.getInt16();
+        if (((len & 1) != 0) || (k + 2 != len)) {
+            throw new SSLProtocolException("Invalid " + type + " extension");
+        }
+        curveIds = new int[k >> 1];
+        for (int i = 0; i < curveIds.length; i++) {
+            curveIds[i] = s.getInt16();
+        }
+    }
+
+    boolean contains(int index) {
+        for (int curveId : curveIds) {
+            if (index == curveId) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    // Return a reference to the internal curveIds array.
+    // The caller must NOT modify the contents.
+    int[] curveIds() {
+        return curveIds;
+    }
+
+    int length() {
+        return 6 + (curveIds.length << 1);
+    }
+
+    void send(HandshakeOutStream s) throws IOException {
+        s.putInt16(type.id);
+        int k = curveIds.length << 1;
+        s.putInt16(k + 2);
+        s.putInt16(k);
+        for (int curveId : curveIds) {
+            s.putInt16(curveId);
+        }
+    }
+
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append("Extension " + type + ", curve names: {");
+        boolean first = true;
+        for (int curveId : curveIds) {
+            if (first) {
+                first = false;
+            } else {
+                sb.append(", ");
+            }
+            // first check if it is a known named curve, then try other cases.
+            String oid = getCurveOid(curveId);
+            if (oid != null) {
+                ECParameterSpec spec = JsseJce.getECParameterSpec(oid);
+                // this toString() output will look nice for the current
+                // implementation of the ECParameterSpec class in the Sun
+                // provider, but may not look good for other implementations.
+                if (spec != null) {
+                    sb.append(spec.toString().split(" ")[0]);
+                } else {
+                    sb.append(oid);
+                }
+            } else if (curveId == ARBITRARY_PRIME) {
+                sb.append("arbitrary_explicit_prime_curves");
+            } else if (curveId == ARBITRARY_CHAR2) {
+                sb.append("arbitrary_explicit_char2_curves");
+            } else {
+                sb.append("unknown curve " + curveId);
+            }
+        }
+        sb.append("}");
+        return sb.toString();
+    }
+
+    // Test whether we support the curve with the given index.
+    static boolean isSupported(int index) {
+        if ((index <= 0) || (index >= NAMED_CURVE_OID_TABLE.length)) {
+            return false;
+        }
+        if (fips == false) {
+            // in non-FIPS mode, we support all valid indices
+            return true;
+        }
+        return DEFAULT.contains(index);
+    }
+
+    static int getCurveIndex(ECParameterSpec params) {
+        String oid = JsseJce.getNamedCurveOid(params);
+        if (oid == null) {
+            return -1;
+        }
+        Integer n = curveIndices.get(oid);
+        return (n == null) ? -1 : n;
+    }
+
+    static String getCurveOid(int index) {
+        if ((index > 0) && (index < NAMED_CURVE_OID_TABLE.length)) {
+            return NAMED_CURVE_OID_TABLE[index];
+        }
+        return null;
+    }
+
+    private final static int ARBITRARY_PRIME = 0xff01;
+    private final static int ARBITRARY_CHAR2 = 0xff02;
+
+    // See sun.security.ec.NamedCurve for the OIDs
+    private final static String[] NAMED_CURVE_OID_TABLE = new String[] {
+        null,                   //  (0) unused
+        "1.3.132.0.1",          //  (1) sect163k1, NIST K-163
+        "1.3.132.0.2",          //  (2) sect163r1
+        "1.3.132.0.15",         //  (3) sect163r2, NIST B-163
+        "1.3.132.0.24",         //  (4) sect193r1
+        "1.3.132.0.25",         //  (5) sect193r2
+        "1.3.132.0.26",         //  (6) sect233k1, NIST K-233
+        "1.3.132.0.27",         //  (7) sect233r1, NIST B-233
+        "1.3.132.0.3",          //  (8) sect239k1
+        "1.3.132.0.16",         //  (9) sect283k1, NIST K-283
+        "1.3.132.0.17",         // (10) sect283r1, NIST B-283
+        "1.3.132.0.36",         // (11) sect409k1, NIST K-409
+        "1.3.132.0.37",         // (12) sect409r1, NIST B-409
+        "1.3.132.0.38",         // (13) sect571k1, NIST K-571
+        "1.3.132.0.39",         // (14) sect571r1, NIST B-571
+        "1.3.132.0.9",          // (15) secp160k1
+        "1.3.132.0.8",          // (16) secp160r1
+        "1.3.132.0.30",         // (17) secp160r2
+        "1.3.132.0.31",         // (18) secp192k1
+        "1.2.840.10045.3.1.1",  // (19) secp192r1, NIST P-192
+        "1.3.132.0.32",         // (20) secp224k1
+        "1.3.132.0.33",         // (21) secp224r1, NIST P-224
+        "1.3.132.0.10",         // (22) secp256k1
+        "1.2.840.10045.3.1.7",  // (23) secp256r1, NIST P-256
+        "1.3.132.0.34",         // (24) secp384r1, NIST P-384
+        "1.3.132.0.35",         // (25) secp521r1, NIST P-521
+    };
+
+    private final static Map<String,Integer> curveIndices;
+
+    static {
+        curveIndices = new HashMap<String,Integer>();
+        for (int i = 1; i < NAMED_CURVE_OID_TABLE.length; i++) {
+            curveIndices.put(NAMED_CURVE_OID_TABLE[i], i);
+        }
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/SupportedEllipticPointFormatsExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,101 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.net.ssl.SSLProtocolException;
+
+final class SupportedEllipticPointFormatsExtension extends HelloExtension {
+
+    final static int FMT_UNCOMPRESSED = 0;
+    final static int FMT_ANSIX962_COMPRESSED_PRIME = 1;
+    final static int FMT_ANSIX962_COMPRESSED_CHAR2 = 2;
+
+    static final HelloExtension DEFAULT =
+        new SupportedEllipticPointFormatsExtension(
+            new byte[] {FMT_UNCOMPRESSED});
+
+    private final byte[] formats;
+
+    private SupportedEllipticPointFormatsExtension(byte[] formats) {
+        super(ExtensionType.EXT_EC_POINT_FORMATS);
+        this.formats = formats;
+    }
+
+    SupportedEllipticPointFormatsExtension(HandshakeInStream s, int len)
+            throws IOException {
+        super(ExtensionType.EXT_EC_POINT_FORMATS);
+        formats = s.getBytes8();
+        // RFC 4492 says uncompressed points must always be supported.
+        // Check just to make sure.
+        boolean uncompressed = false;
+        for (int format : formats) {
+            if (format == FMT_UNCOMPRESSED) {
+                uncompressed = true;
+                break;
+            }
+        }
+        if (uncompressed == false) {
+            throw new SSLProtocolException
+                ("Peer does not support uncompressed points");
+        }
+    }
+
+    int length() {
+        return 5 + formats.length;
+    }
+
+    void send(HandshakeOutStream s) throws IOException {
+        s.putInt16(type.id);
+        s.putInt16(formats.length + 1);
+        s.putBytes8(formats);
+    }
+
+    private static String toString(byte format) {
+        int f = format & 0xff;
+        switch (f) {
+        case FMT_UNCOMPRESSED:
+            return "uncompressed";
+        case FMT_ANSIX962_COMPRESSED_PRIME:
+            return "ansiX962_compressed_prime";
+        case FMT_ANSIX962_COMPRESSED_CHAR2:
+            return "ansiX962_compressed_char2";
+        default:
+            return "unknown-" + f;
+        }
+    }
+
+    public String toString() {
+        List<String> list = new ArrayList<String>();
+        for (byte format : formats) {
+            list.add(toString(format));
+        }
+        return "Extension " + type + ", formats: " + list;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/share/classes/sun/security/ssl/UnknownExtension.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2006, 2011, 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.security.ssl;
+
+import java.io.IOException;
+
+final class UnknownExtension extends HelloExtension {
+
+    private final byte[] data;
+
+    UnknownExtension(HandshakeInStream s, int len, ExtensionType type)
+            throws IOException {
+        super(type);
+        data = new byte[len];
+        // s.read() does not handle 0-length arrays.
+        if (len != 0) {
+            s.read(data);
+        }
+    }
+
+    int length() {
+        return 4 + data.length;
+    }
+
+    void send(HandshakeOutStream s) throws IOException {
+        s.putInt16(type.id);
+        s.putBytes16(data);
+    }
+
+    public String toString() {
+        return "Unsupported extension " + type + ", data: " +
+            Debug.toString(data);
+    }
+}
--- a/src/share/classes/sun/util/locale/provider/JRELocaleProviderAdapter.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/util/locale/provider/JRELocaleProviderAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -321,7 +321,7 @@
         while (tokens.hasMoreTokens()) {
             String token = tokens.nextToken();
             if (token.equals("|")) {
-                if (isNonEuroLangSupported()) {
+                if (isNonUSLangSupported()) {
                     continue;
                 }
                 break;
@@ -361,7 +361,7 @@
          */
         int barIndex = supportedLocaleString.indexOf('|');
         StringTokenizer localeStringTokenizer;
-        if (isNonEuroLangSupported()) {
+        if (isNonUSLangSupported()) {
             localeStringTokenizer = new StringTokenizer(supportedLocaleString.substring(0, barIndex)
                     + supportedLocaleString.substring(barIndex + 1));
         } else {
@@ -390,17 +390,17 @@
         return locales;
     }
 
-    private static volatile Boolean isNonEuroSupported = null;
+    private static volatile Boolean isNonUSSupported = null;
 
     /*
-     * Returns true if the non European resources jar file exists in jre
+     * Returns true if the non US resources jar file exists in jre
      * extension directory. @returns true if the jar file is there. Otherwise,
      * returns false.
      */
-    private static boolean isNonEuroLangSupported() {
-        if (isNonEuroSupported == null) {
+    private static boolean isNonUSLangSupported() {
+        if (isNonUSSupported == null) {
             synchronized (JRELocaleProviderAdapter.class) {
-                if (isNonEuroSupported == null) {
+                if (isNonUSSupported == null) {
                     final String sep = File.separator;
                     String localeDataJar =
                             java.security.AccessController.doPrivileged(
@@ -412,7 +412,7 @@
                      * localedata.jar is installed or not.
                      */
                     final File f = new File(localeDataJar);
-                    isNonEuroSupported =
+                    isNonUSSupported =
                         AccessController.doPrivileged(new PrivilegedAction<Boolean>() {
                             @Override
                             public Boolean run() {
@@ -422,6 +422,6 @@
                }
             }
         }
-        return isNonEuroSupported;
+        return isNonUSSupported;
     }
 }
--- a/src/share/classes/sun/util/locale/provider/LocaleDataMetaInfo-XLocales.java.template	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/util/locale/provider/LocaleDataMetaInfo-XLocales.java.template	Mon Nov 05 10:33:18 2012 -0500
@@ -52,25 +52,25 @@
            look up locale string such as "en" could be based on if it contains " en ".
         */
         resourceNameToLocales.put("FormatData",
-                                  " #FormatData_EuroLocales# | #FormatData_NonEuroLocales# ");
+                                  " #FormatData_USLocales# | #FormatData_NonUSLocales# ");
 
         resourceNameToLocales.put("CollationData",
-                                  " #CollationData_EuroLocales# | #CollationData_NonEuroLocales# ");
+                                  " #CollationData_USLocales# | #CollationData_NonUSLocales# ");
 
         resourceNameToLocales.put("TimeZoneNames",
-                                  " #TimeZoneNames_EuroLocales# | #TimeZoneNames_NonEuroLocales# ");
+                                  " #TimeZoneNames_USLocales# | #TimeZoneNames_NonUSLocales# ");
 
         resourceNameToLocales.put("LocaleNames",
-                                  " #LocaleNames_EuroLocales# | #LocaleNames_NonEuroLocales# ");
+                                  " #LocaleNames_USLocales# | #LocaleNames_NonUSLocales# ");
 
         resourceNameToLocales.put("CurrencyNames",
-                                  " #CurrencyNames_EuroLocales# | #CurrencyNames_NonEuroLocales# ");
+                                  " #CurrencyNames_USLocales# | #CurrencyNames_NonUSLocales# ");
 
         resourceNameToLocales.put("CalendarData",
-                                  " #CalendarData_EuroLocales# | #CalendarData_NonEuroLocales# ");
+                                  " #CalendarData_USLocales# | #CalendarData_NonUSLocales# ");
 
         resourceNameToLocales.put("AvailableLocales",
-                                  " #AvailableLocales_EuroLocales# | #AvailableLocales_NonEuroLocales# ");
+                                  " #AvailableLocales_USLocales# | #AvailableLocales_NonUSLocales# ");
     }
 
     /*
--- a/src/share/classes/sun/util/locale/provider/LocaleServiceProviderPool.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/util/locale/provider/LocaleServiceProviderPool.java	Mon Nov 05 10:33:18 2012 -0500
@@ -356,7 +356,7 @@
      * @param locale the input locale
      * @return the list of candidate locales for the given locale
      */
-    private static List<Locale> getLookupLocales(Locale locale) {
+    static List<Locale> getLookupLocales(Locale locale) {
         // Note: We currently use the default implementation of
         // ResourceBundle.Control.getCandidateLocales. The result
         // returned by getCandidateLocales are already normalized
--- a/src/share/classes/sun/util/locale/provider/SPILocaleProviderAdapter.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/classes/sun/util/locale/provider/SPILocaleProviderAdapter.java	Mon Nov 05 10:33:18 2012 -0500
@@ -28,8 +28,11 @@
 import java.security.AccessController;
 import java.security.PrivilegedActionException;
 import java.security.PrivilegedExceptionAction;
-import java.util.ServiceLoader;
-import java.util.spi.LocaleServiceProvider;
+import java.text.*;
+import java.text.spi.*;
+import java.util.*;
+import java.util.concurrent.*;
+import java.util.spi.*;
 
 /**
  * LocaleProviderAdapter implementation for the installed SPI implementations.
@@ -54,11 +57,28 @@
                 @Override
                 @SuppressWarnings("unchecked")
                 public P run() {
-                    P lsp = null;
+                    P delegate = null;
+
                     for (LocaleServiceProvider provider : ServiceLoader.loadInstalled(c)) {
-                        lsp = (P) provider;
+                        if (delegate == null) {
+                            try {
+                                delegate =
+                                    (P) Class.forName(SPILocaleProviderAdapter.class.getCanonicalName() +
+                                              "$" +
+                                              c.getSimpleName() +
+                                              "Delegate")
+                                              .newInstance();
+                            }  catch (ClassNotFoundException |
+                                      InstantiationException |
+                                      IllegalAccessException e) {
+                                LocaleServiceProviderPool.config(SPILocaleProviderAdapter.class, e.toString());
+                                return null;
                     }
-                    return lsp;
+                        }
+
+                        ((Delegate)delegate).addImpl(provider);
+                    }
+                    return delegate;
                 }
             });
         }  catch (PrivilegedActionException e) {
@@ -66,4 +86,478 @@
         }
         return null;
     }
+
+    /*
+     * Delegate interface. All the implementations have to have the class name
+     * following "<provider class name>Delegate" convention.
+     */
+    interface Delegate<P extends LocaleServiceProvider> {
+        public void addImpl(P impl);
+        public P getImpl(Locale locale);
 }
+
+    /*
+     * Obtain the real SPI implementation, using locale fallback
+     */
+    private static <P extends LocaleServiceProvider> P getImpl(Map<Locale, P> map, Locale locale) {
+        for (Locale l : LocaleServiceProviderPool.getLookupLocales(locale)) {
+            P ret = map.get(l);
+            if (ret != null) {
+                return ret;
+            }
+        }
+        return null;
+    }
+
+    /*
+     * Delegates for the actual SPI implementations.
+     */
+    static class BreakIteratorProviderDelegate extends BreakIteratorProvider
+                                        implements Delegate<BreakIteratorProvider> {
+        private ConcurrentMap<Locale, BreakIteratorProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(BreakIteratorProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public BreakIteratorProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public BreakIterator getWordInstance(Locale locale) {
+            BreakIteratorProvider bip = getImpl(locale);
+            assert bip != null;
+            return bip.getWordInstance(locale);
+        }
+
+        @Override
+        public BreakIterator getLineInstance(Locale locale) {
+            BreakIteratorProvider bip = getImpl(locale);
+            assert bip != null;
+            return bip.getLineInstance(locale);
+        }
+
+        @Override
+        public BreakIterator getCharacterInstance(Locale locale) {
+            BreakIteratorProvider bip = getImpl(locale);
+            assert bip != null;
+            return bip.getCharacterInstance(locale);
+        }
+
+        @Override
+        public BreakIterator getSentenceInstance(Locale locale) {
+            BreakIteratorProvider bip = getImpl(locale);
+            assert bip != null;
+            return bip.getSentenceInstance(locale);
+        }
+
+    }
+
+    static class CollatorProviderDelegate extends CollatorProvider implements Delegate<CollatorProvider> {
+        private ConcurrentMap<Locale, CollatorProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(CollatorProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public CollatorProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public Collator getInstance(Locale locale) {
+            CollatorProvider cp = getImpl(locale);
+            assert cp != null;
+            return cp.getInstance(locale);
+        }
+    }
+
+    static class DateFormatProviderDelegate extends DateFormatProvider
+                                     implements Delegate<DateFormatProvider> {
+        private ConcurrentMap<Locale, DateFormatProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(DateFormatProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public DateFormatProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public DateFormat getTimeInstance(int style, Locale locale) {
+            DateFormatProvider dfp = getImpl(locale);
+            assert dfp != null;
+            return dfp.getTimeInstance(style, locale);
+        }
+
+        @Override
+        public DateFormat getDateInstance(int style, Locale locale) {
+            DateFormatProvider dfp = getImpl(locale);
+            assert dfp != null;
+            return dfp.getDateInstance(style, locale);
+        }
+
+        @Override
+        public DateFormat getDateTimeInstance(int dateStyle, int timeStyle, Locale locale) {
+            DateFormatProvider dfp = getImpl(locale);
+            assert dfp != null;
+            return dfp.getDateTimeInstance(dateStyle, timeStyle, locale);
+        }
+    }
+
+    static class DateFormatSymbolsProviderDelegate extends DateFormatSymbolsProvider
+                                            implements Delegate<DateFormatSymbolsProvider> {
+        private ConcurrentMap<Locale, DateFormatSymbolsProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(DateFormatSymbolsProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public DateFormatSymbolsProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public DateFormatSymbols getInstance(Locale locale) {
+            DateFormatSymbolsProvider dfsp = getImpl(locale);
+            assert dfsp != null;
+            return dfsp.getInstance(locale);
+        }
+    }
+
+    static class DecimalFormatSymbolsProviderDelegate extends DecimalFormatSymbolsProvider
+                                               implements Delegate<DecimalFormatSymbolsProvider> {
+        private ConcurrentMap<Locale, DecimalFormatSymbolsProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(DecimalFormatSymbolsProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public DecimalFormatSymbolsProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public DecimalFormatSymbols getInstance(Locale locale) {
+            DecimalFormatSymbolsProvider dfsp = getImpl(locale);
+            assert dfsp != null;
+            return dfsp.getInstance(locale);
+        }
+    }
+
+    static class NumberFormatProviderDelegate extends NumberFormatProvider
+                                       implements Delegate<NumberFormatProvider> {
+        private ConcurrentMap<Locale, NumberFormatProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(NumberFormatProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public NumberFormatProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public NumberFormat getCurrencyInstance(Locale locale) {
+            NumberFormatProvider nfp = getImpl(locale);
+            assert nfp != null;
+            return nfp.getCurrencyInstance(locale);
+        }
+
+        @Override
+        public NumberFormat getIntegerInstance(Locale locale) {
+            NumberFormatProvider nfp = getImpl(locale);
+            assert nfp != null;
+            return nfp.getIntegerInstance(locale);
+        }
+
+        @Override
+        public NumberFormat getNumberInstance(Locale locale) {
+            NumberFormatProvider nfp = getImpl(locale);
+            assert nfp != null;
+            return nfp.getNumberInstance(locale);
+        }
+
+        @Override
+        public NumberFormat getPercentInstance(Locale locale) {
+            NumberFormatProvider nfp = getImpl(locale);
+            assert nfp != null;
+            return nfp.getPercentInstance(locale);
+        }
+    }
+
+    static class CalendarDataProviderDelegate extends CalendarDataProvider
+                                       implements Delegate<CalendarDataProvider> {
+        private ConcurrentMap<Locale, CalendarDataProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(CalendarDataProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public CalendarDataProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public int getFirstDayOfWeek(Locale locale) {
+            CalendarDataProvider cdp = getImpl(locale);
+            assert cdp != null;
+            return cdp.getFirstDayOfWeek(locale);
+        }
+
+        @Override
+        public int getMinimalDaysInFirstWeek(Locale locale) {
+            CalendarDataProvider cdp = getImpl(locale);
+            assert cdp != null;
+            return cdp.getMinimalDaysInFirstWeek(locale);
+        }
+
+        @Override
+        public String getDisplayName(String calendarType,
+                                              int field, int value,
+                                              int style, Locale locale) {
+            CalendarDataProvider cdp = getImpl(locale);
+            assert cdp != null;
+            return cdp.getDisplayName(calendarType, field, value, style, locale);
+        }
+
+        @Override
+        public Map<String, Integer> getDisplayNames(String calendarType,
+                                                             int field, int style,
+                                                             Locale locale) {
+            CalendarDataProvider cdp = getImpl(locale);
+            assert cdp != null;
+            return cdp.getDisplayNames(calendarType, field, style, locale);
+        }
+    }
+
+    static class CurrencyNameProviderDelegate extends CurrencyNameProvider
+                                       implements Delegate<CurrencyNameProvider> {
+        private ConcurrentMap<Locale, CurrencyNameProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(CurrencyNameProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public CurrencyNameProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public String getSymbol(String currencyCode, Locale locale) {
+            CurrencyNameProvider cnp = getImpl(locale);
+            assert cnp != null;
+            return cnp.getSymbol(currencyCode, locale);
+        }
+
+        @Override
+        public String getDisplayName(String currencyCode, Locale locale) {
+            CurrencyNameProvider cnp = getImpl(locale);
+            assert cnp != null;
+            return cnp.getDisplayName(currencyCode, locale);
+        }
+    }
+
+    static class LocaleNameProviderDelegate extends LocaleNameProvider
+                                     implements Delegate<LocaleNameProvider> {
+        private ConcurrentMap<Locale, LocaleNameProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(LocaleNameProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public LocaleNameProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public String getDisplayLanguage(String languageCode, Locale locale) {
+            LocaleNameProvider lnp = getImpl(locale);
+            assert lnp != null;
+            return lnp.getDisplayLanguage(languageCode, locale);
+        }
+
+        @Override
+        public String getDisplayScript(String scriptCode, Locale locale) {
+            LocaleNameProvider lnp = getImpl(locale);
+            assert lnp != null;
+            return lnp.getDisplayScript(scriptCode, locale);
+        }
+
+        @Override
+        public String getDisplayCountry(String countryCode, Locale locale) {
+            LocaleNameProvider lnp = getImpl(locale);
+            assert lnp != null;
+            return lnp.getDisplayCountry(countryCode, locale);
+        }
+
+        @Override
+        public String getDisplayVariant(String variant, Locale locale) {
+            LocaleNameProvider lnp = getImpl(locale);
+            assert lnp != null;
+            return lnp.getDisplayVariant(variant, locale);
+        }
+    }
+
+    static class TimeZoneNameProviderDelegate extends TimeZoneNameProvider
+                                     implements Delegate<TimeZoneNameProvider> {
+        private ConcurrentMap<Locale, TimeZoneNameProvider> map = new ConcurrentHashMap<>();
+
+        @Override
+        public void addImpl(TimeZoneNameProvider impl) {
+            for (Locale l : impl.getAvailableLocales()) {
+                map.put(l, impl);
+            }
+        }
+
+        @Override
+        public TimeZoneNameProvider getImpl(Locale locale) {
+            return SPILocaleProviderAdapter.getImpl(map, locale);
+        }
+
+        @Override
+        public Locale[] getAvailableLocales() {
+            return map.keySet().toArray(new Locale[0]);
+        }
+
+        @Override
+        public boolean isSupportedLocale(Locale locale) {
+            return map.containsKey(locale);
+        }
+
+        @Override
+        public String getDisplayName(String ID, boolean daylight, int style, Locale locale) {
+            TimeZoneNameProvider tznp = getImpl(locale);
+            assert tznp != null;
+            return tznp.getDisplayName(ID, daylight, style, locale);
+        }
+    }
+}
--- a/src/share/lib/security/java.security	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/lib/security/java.security	Mon Nov 05 10:33:18 2012 -0500
@@ -145,7 +145,7 @@
 # passed to checkPackageAccess unless the
 # corresponding RuntimePermission ("accessClassInPackage."+package) has
 # been granted.
-package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # List of comma-separated packages that start with or equal this string
@@ -157,7 +157,7 @@
 # by default, none of the class loaders supplied with the JDK call
 # checkPackageDefinition.
 #
-package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # Determines whether this properties file can be appended to
--- a/src/share/lib/security/java.security-macosx	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/lib/security/java.security-macosx	Mon Nov 05 10:33:18 2012 -0500
@@ -146,7 +146,7 @@
 # passed to checkPackageAccess unless the
 # corresponding RuntimePermission ("accessClassInPackage."+package) has
 # been granted.
-package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,apple.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,apple.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # List of comma-separated packages that start with or equal this string
@@ -158,7 +158,7 @@
 # by default, none of the class loaders supplied with the JDK call
 # checkPackageDefinition.
 #
-package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,apple.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,apple.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # Determines whether this properties file can be appended to
--- a/src/share/lib/security/java.security-solaris	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/lib/security/java.security-solaris	Mon Nov 05 10:33:18 2012 -0500
@@ -147,7 +147,7 @@
 # passed to checkPackageAccess unless the
 # corresponding RuntimePermission ("accessClassInPackage."+package) has
 # been granted.
-package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # List of comma-separated packages that start with or equal this string
@@ -159,7 +159,7 @@
 # by default, none of the class loaders supplied with the JDK call
 # checkPackageDefinition.
 #
-package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # Determines whether this properties file can be appended to
--- a/src/share/lib/security/java.security-windows	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/lib/security/java.security-windows	Mon Nov 05 10:33:18 2012 -0500
@@ -146,7 +146,7 @@
 # passed to checkPackageAccess unless the
 # corresponding RuntimePermission ("accessClassInPackage."+package) has
 # been granted.
-package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.access=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # List of comma-separated packages that start with or equal this string
@@ -158,7 +158,7 @@
 # by default, none of the class loaders supplied with the JDK call
 # checkPackageDefinition.
 #
-package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.
+package.definition=sun.,com.sun.xml.internal.ws.,com.sun.xml.internal.bind.,com.sun.imageio.,com.sun.org.apache.xerces.internal.utils.,com.sun.org.apache.xalan.internal.utils.,com.sun.org.glassfish.external.,com.sun.org.glassfish.gmbal.,jdk.internal.
 
 #
 # Determines whether this properties file can be appended to
--- a/src/share/native/sun/java2d/cmm/lcms/LCMS.c	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/share/native/sun/java2d/cmm/lcms/LCMS.c	Mon Nov 05 10:33:18 2012 -0500
@@ -253,6 +253,16 @@
 
     if (sProf.pf == NULL) {
         JNU_ThrowIllegalArgumentException(env, "Invalid profile data");
+    } else {
+        /* Sanity check: try to save the profile in order
+         * to force basic validation.
+         */
+        cmsUInt32Number pfSize = 0;
+        if (!cmsSaveProfileToMem(sProf.pf, NULL, &pfSize) ||
+            pfSize < sizeof(cmsICCHeader))
+        {
+            JNU_ThrowIllegalArgumentException(env, "Invalid profile data");
+        }
     }
 
     return sProf.j;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/solaris/classes/java/io/DefaultFileSystem.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2012, 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 java.io;
+
+/**
+ *
+ * @since 1.8
+ */
+class DefaultFileSystem {
+
+    /**
+     * Return the FileSystem object for Unix-based platform.
+     */
+    public static FileSystem getFileSystem() {
+        return new UnixFileSystem();
+    }
+}
--- a/src/solaris/classes/sun/awt/X11/XChoicePeer.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/classes/sun/awt/X11/XChoicePeer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1108,17 +1108,3 @@
         return true;
     }
 }
-
-/*
- * The listener interface for receiving "interesting" for XFileDialogPeer
- * choice events (opening, closing).
- * The listener added by means of the method addXChoicePeerListener
- * A opening choice event is generated when the invoking unfurledChoice.toFront()
- * A closing choice event is generated at the time of the processing the mouse releasing
- * and the Enter pressing.
- * see 6240074 for more information
- */
-interface XChoicePeerListener{
-    public void unfurledChoiceOpening(ListHelper choiceHelper);
-    public void unfurledChoiceClosing();
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/solaris/classes/sun/awt/X11/XChoicePeerListener.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2003, 2007, 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.awt.X11;
+
+/*
+ * The listener interface for receiving "interesting" for XFileDialogPeer
+ * choice events (opening, closing).
+ * The listener added by means of the method addXChoicePeerListener
+ * A opening choice event is generated when the invoking unfurledChoice.toFront()
+ * A closing choice event is generated at the time of the processing the mouse releasing
+ * and the Enter pressing.
+ * see 6240074 for more information
+ */
+interface XChoicePeerListener{
+    public void unfurledChoiceOpening(ListHelper choiceHelper);
+    public void unfurledChoiceClosing();
+}
--- a/src/solaris/classes/sun/awt/X11/XKeysym.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/classes/sun/awt/X11/XKeysym.java	Mon Nov 05 10:33:18 2012 -0500
@@ -379,6 +379,25 @@
         keysym2UCSHash.put( (long)0xFFB8, (char)0x0038); // XK_KP_8 --> DIGIT EIGHT
         keysym2UCSHash.put( (long)0xFFB9, (char)0x0039); // XK_KP_9 --> DIGIT NINE
         keysym2UCSHash.put( (long)0xFE20, (char)0x0009); // XK_ISO_Left_Tab --> <control>
+        keysym2UCSHash.put( (long)0xFE50, (char)0x02CB); // XK_dead_grave --> MODIFIER LETTER GRAVE ACCENT
+        keysym2UCSHash.put( (long)0xFE51, (char)0x02CA); // XK_dead_acute --> MODIFIER LETTER ACUTE ACCENT
+        keysym2UCSHash.put( (long)0xFE52, (char)0x02C6); // XK_dead_circumflex --> MODIFIER LETTER CIRCUMFLEX ACCENT
+        keysym2UCSHash.put( (long)0xFE53, (char)0x02DC); // XK_dead_tilde --> SMALL TILDE
+        keysym2UCSHash.put( (long)0xFE54, (char)0x02C9); // XK_dead_macron --> MODIFIER LETTER MACRON
+        keysym2UCSHash.put( (long)0xFE55, (char)0x02D8); // XK_dead_breve --> BREVE
+        keysym2UCSHash.put( (long)0xFE56, (char)0x02D9); // XK_dead_abovedot --> DOT ABOVE
+        keysym2UCSHash.put( (long)0xFE57, (char)0x00A8); // XK_dead_diaeresis --> DIAERESIS
+        keysym2UCSHash.put( (long)0xFE58, (char)0x02DA); // XK_dead_abovering --> RING ABOVE
+        keysym2UCSHash.put( (long)0xFE59, (char)0x02DD); // XK_dead_doubleacute --> DOUBLE ACUTE ACCENT
+        keysym2UCSHash.put( (long)0xFE5A, (char)0x02C7); // XK_dead_caron --> CARON
+        keysym2UCSHash.put( (long)0xFE5B, (char)0x00B8); // XK_dead_cedilla --> CEDILLA
+        keysym2UCSHash.put( (long)0xFE5C, (char)0x02DB); // XK_dead_ogonek --> OGONEK
+        keysym2UCSHash.put( (long)0xFE5D, (char)0x0269); // XK_dead_iota --> LATIN SMALL LETTER IOTA
+        keysym2UCSHash.put( (long)0xFE5E, (char)0x3099); // XK_dead_voiced_sound --> COMBINING KATAKANA-HIRAGANA VOICED SOUND MARK
+        keysym2UCSHash.put( (long)0xFE5F, (char)0x309A); // XK_dead_semivoiced_sound --> COMBINING KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK
+        keysym2UCSHash.put( (long)0xFE60, (char)0x0323); // XK_dead_belowdot --> COMBINING DOT BELOW
+        keysym2UCSHash.put( (long)0xFE61, (char)0x0321); // XK_dead_hook --> COMBINING PALATALIZED HOOK BELOW
+        keysym2UCSHash.put( (long)0xFE62, (char)0x031B); // XK_dead_horn --> COMBINING HORN
         keysym2UCSHash.put( (long)0x1a1, (char)0x0104); // XK_Aogonek --> LATIN CAPITAL LETTER A WITH OGONEK
         keysym2UCSHash.put( (long)0x1a2, (char)0x02d8); // XK_breve --> BREVE
         keysym2UCSHash.put( (long)0x1a3, (char)0x0141); // XK_Lstroke --> LATIN CAPITAL LETTER L WITH STROKE
--- a/src/solaris/classes/sun/awt/X11/XWindow.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/classes/sun/awt/X11/XWindow.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1115,7 +1115,10 @@
         //  (1) either XIM could not handle it or
         //  (2) it was Latin 1:1 mapping.
         //
-        XKeysym.Keysym2JavaKeycode jkc = XKeysym.getJavaKeycode(ev);
+        // Preserve modifiers to get Java key code for dead keys
+        boolean isDeadKey = isDeadKey(keysym[0]);
+        XKeysym.Keysym2JavaKeycode jkc = isDeadKey ? XKeysym.getJavaKeycode(keysym[0])
+                : XKeysym.getJavaKeycode(ev);
         if( jkc == null ) {
             jkc = new XKeysym.Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_UNDEFINED, java.awt.event.KeyEvent.KEY_LOCATION_UNKNOWN);
         }
@@ -1141,7 +1144,7 @@
                              jkc.getJavaKeycode();
         postKeyEvent( java.awt.event.KeyEvent.KEY_PRESSED,
                           ev.get_time(),
-                          jkeyToReturn,
+                          isDeadKey ? jkeyExtended : jkeyToReturn,
                           (unicodeKey == 0 ? java.awt.event.KeyEvent.CHAR_UNDEFINED : unicodeKey),
                           jkc.getKeyLocation(),
                           ev.get_state(),ev.getPData(), XKeyEvent.getSize(), (long)(ev.get_keycode()),
@@ -1149,7 +1152,7 @@
                           jkeyExtended);
 
 
-        if( unicodeKey > 0 ) {
+        if (unicodeKey > 0 && !isDeadKey) {
                 keyEventLog.fine("fire _TYPED on "+unicodeKey);
                 postKeyEvent( java.awt.event.KeyEvent.KEY_TYPED,
                               ev.get_time(),
@@ -1176,9 +1179,7 @@
     }
     // un-private it if you need to call it from elsewhere
     private void handleKeyRelease(XKeyEvent ev) {
-        long keysym[] = new long[2];
         int unicodeKey = 0;
-        keysym[0] = XConstants.NoSymbol;
 
         if (keyEventLog.isLoggable(PlatformLogger.FINE)) {
             logIncomingKeyEvent( ev );
@@ -1187,7 +1188,11 @@
         // and Java KeyEvent keycode should be calculated.
         // For release we should post released event.
         //
-        XKeysym.Keysym2JavaKeycode jkc = XKeysym.getJavaKeycode(ev);
+        // Preserve modifiers to get Java key code for dead keys
+        long keysym = xkeycodeToKeysym(ev);
+        boolean isDeadKey = isDeadKey(keysym);
+        XKeysym.Keysym2JavaKeycode jkc = isDeadKey ? XKeysym.getJavaKeycode(keysym)
+                : XKeysym.getJavaKeycode(ev);
         if( jkc == null ) {
             jkc = new XKeysym.Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_UNDEFINED, java.awt.event.KeyEvent.KEY_LOCATION_UNKNOWN);
         }
@@ -1219,7 +1224,7 @@
                              jkc.getJavaKeycode();
         postKeyEvent(  java.awt.event.KeyEvent.KEY_RELEASED,
                           ev.get_time(),
-                          jkeyToReturn,
+                          isDeadKey ? jkeyExtended : jkeyToReturn,
                           (unicodeKey == 0 ? java.awt.event.KeyEvent.CHAR_UNDEFINED : unicodeKey),
                           jkc.getKeyLocation(),
                           ev.get_state(),ev.getPData(), XKeyEvent.getSize(), (long)(ev.get_keycode()),
@@ -1229,6 +1234,11 @@
 
     }
 
+
+    private boolean isDeadKey(long keysym){
+        return XKeySymConstants.XK_dead_grave <= keysym && keysym <= XKeySymConstants.XK_dead_semivoiced_sound;
+    }
+
     /*
      * XmNiconic and Map/UnmapNotify (that XmNiconic relies on) are
      * unreliable, since mapping changes can happen for a virtual desktop
--- a/src/solaris/classes/sun/awt/X11/keysym2ucs.h	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/classes/sun/awt/X11/keysym2ucs.h	Mon Nov 05 10:33:18 2012 -0500
@@ -695,25 +695,25 @@
 0x0000 #define    XK_ISO_Center_Object                0xFE33
 0x0000 #define    XK_ISO_Enter                    0xFE34
 
-0x0000 #define    XK_dead_grave                    0xFE50
-0x0000 #define    XK_dead_acute                    0xFE51
-0x0000 #define    XK_dead_circumflex                0xFE52
-0x0000 #define    XK_dead_tilde                    0xFE53
-0x0000 #define    XK_dead_macron                    0xFE54
-0x0000 #define    XK_dead_breve                    0xFE55
-0x0000 #define    XK_dead_abovedot                0xFE56
-0x0000 #define    XK_dead_diaeresis                0xFE57
-0x0000 #define    XK_dead_abovering                0xFE58
-0x0000 #define    XK_dead_doubleacute                0xFE59
-0x0000 #define    XK_dead_caron                    0xFE5A
-0x0000 #define    XK_dead_cedilla                    0xFE5B
-0x0000 #define    XK_dead_ogonek                    0xFE5C
-0x0000 #define    XK_dead_iota                    0xFE5D
-0x0000 #define    XK_dead_voiced_sound                0xFE5E
-0x0000 #define    XK_dead_semivoiced_sound            0xFE5F
-0x0000 #define    XK_dead_belowdot                0xFE60
-0x0000 #define XK_dead_hook                    0xFE61
-0x0000 #define XK_dead_horn                    0xFE62
+0x02CB #define    XK_dead_grave                    0xFE50
+0x02CA #define    XK_dead_acute                    0xFE51
+0x02C6 #define    XK_dead_circumflex                0xFE52
+0x02DC #define    XK_dead_tilde                    0xFE53
+0x02C9 #define    XK_dead_macron                    0xFE54
+0x02D8 #define    XK_dead_breve                    0xFE55
+0x02D9 #define    XK_dead_abovedot                0xFE56
+0x00A8 #define    XK_dead_diaeresis                0xFE57
+0x02DA #define    XK_dead_abovering                0xFE58
+0x02DD #define    XK_dead_doubleacute                0xFE59
+0x02C7 #define    XK_dead_caron                    0xFE5A
+0x00B8 #define    XK_dead_cedilla                    0xFE5B
+0x02DB #define    XK_dead_ogonek                    0xFE5C
+0x0269 #define    XK_dead_iota                    0xFE5D
+0x3099 #define    XK_dead_voiced_sound                0xFE5E
+0x309A #define    XK_dead_semivoiced_sound            0xFE5F
+0x0323 #define    XK_dead_belowdot                0xFE60
+0x0321 #define XK_dead_hook                    0xFE61
+0x031B #define XK_dead_horn                    0xFE62
 
 0x0000 #define    XK_First_Virtual_Screen                0xFED0
 0x0000 #define    XK_Prev_Virtual_Screen                0xFED1
@@ -2466,6 +2466,7 @@
 tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Meta_L),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_META, java.awt.event.KeyEvent.KEY_LOCATION_LEFT));
 tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Meta_R),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_META, java.awt.event.KeyEvent.KEY_LOCATION_RIGHT));
 tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Caps_Lock),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_CAPS_LOCK, java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Shift_Lock),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_CAPS_LOCK, java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
 tojava
 tojava             /* Misc Functions */
 tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Print),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_PRINTSCREEN, java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
@@ -2640,6 +2641,21 @@
 tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Kanji),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_CONVERT, java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
 tojava             /* Type 5c Japanese keyboard: nihongo */
 tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Henkan_Mode),     new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_INPUT_METHOD_ON_OFF, java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Eisu_Shift   ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_ALPHANUMERIC       , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Eisu_toggle  ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_ALPHANUMERIC       , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Zenkaku      ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_FULL_WIDTH         , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Hankaku      ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_HALF_WIDTH         , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Hiragana     ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_HIRAGANA           , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Katakana     ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_KATAKANA           , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Romaji       ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_JAPANESE_ROMAN     , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Kana_Shift   ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_KANA               , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Kana_Lock    ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_KANA_LOCK          , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Muhenkan     ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_NONCONVERT         , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Zen_Koho     ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_ALL_CANDIDATES     , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Kanji_Bangou ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_CODE_INPUT         , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava         keysym2JavaKeycodeHash.put( Long.valueOf(XKeySymConstants.XK_Mae_Koho     ), new Keysym2JavaKeycode(java.awt.event.KeyEvent.VK_PREVIOUS_CANDIDATE , java.awt.event.KeyEvent.KEY_LOCATION_STANDARD));
+tojava
+tojava
 tojava             /* VK_KANA_LOCK is handled separately because it generates the
 tojava              * same keysym as ALT_GRAPH in spite of its different behavior.
 tojava              */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/solaris/classes/sun/font/DelegateStrike.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,114 @@
+/*
+ * Copyright (c) 2003, 2004, 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.font;
+
+import java.awt.geom.GeneralPath;
+import java.awt.geom.Point2D;
+import java.awt.Rectangle;
+import java.awt.geom.Rectangle2D;
+
+/* Returned instead of a NativeStrike.
+ * It can intercept any request it wants, but mostly
+ * passes them on to its delegate strike. It is important that
+ * it override all the inherited FontStrike methods to delegate them
+ * appropriately.
+ */
+
+class DelegateStrike extends NativeStrike {
+
+    private FontStrike delegateStrike;
+
+    DelegateStrike(NativeFont nativeFont, FontStrikeDesc desc,
+                   FontStrike delegate) {
+        super(nativeFont, desc);
+        this.delegateStrike = delegate;
+    }
+
+    /* We want the native font to be responsible for reporting the
+     * font metrics, even if it often delegates to another font.
+     * The code here isn't yet implementing exactly that. If the glyph
+     * transform was something native couldn't handle, there's no native
+     * context from which to obtain metrics. Need to revise this to obtain
+     * the metrics and transform them. But currently in such a case it
+     * gets the metrics from a different font - its glyph delegate font.
+     */
+   StrikeMetrics getFontMetrics() {
+       if (strikeMetrics == null) {
+           if (pScalerContext != 0) {
+               strikeMetrics = super.getFontMetrics();
+           }
+            if (strikeMetrics == null) {
+                strikeMetrics = delegateStrike.getFontMetrics();
+            }
+        }
+        return strikeMetrics;
+    }
+
+    void getGlyphImagePtrs(int[] glyphCodes, long[] images,int  len) {
+        delegateStrike.getGlyphImagePtrs(glyphCodes, images, len);
+    }
+
+    long getGlyphImagePtr(int glyphCode) {
+        return delegateStrike.getGlyphImagePtr(glyphCode);
+    }
+
+    void getGlyphImageBounds(int glyphCode,
+                             Point2D.Float pt, Rectangle result) {
+        delegateStrike.getGlyphImageBounds(glyphCode, pt, result);
+    }
+
+    Point2D.Float getGlyphMetrics(int glyphCode) {
+        return delegateStrike.getGlyphMetrics(glyphCode);
+    }
+
+    float getGlyphAdvance(int glyphCode) {
+        return delegateStrike.getGlyphAdvance(glyphCode);
+    }
+
+     Point2D.Float getCharMetrics(char ch) {
+        return delegateStrike.getCharMetrics(ch);
+    }
+
+    float getCodePointAdvance(int cp) {
+        if (cp < 0 || cp >= 0x10000) {
+            cp = 0xffff;
+        }
+        return delegateStrike.getGlyphAdvance(cp);
+    }
+
+    Rectangle2D.Float getGlyphOutlineBounds(int glyphCode) {
+        return delegateStrike.getGlyphOutlineBounds(glyphCode);
+    }
+
+    GeneralPath getGlyphOutline(int glyphCode, float x, float y) {
+        return delegateStrike.getGlyphOutline(glyphCode, x, y);
+    }
+
+    GeneralPath getGlyphVectorOutline(int[] glyphs, float x, float y) {
+        return delegateStrike.getGlyphVectorOutline(glyphs, x, y);
+    }
+
+}
--- a/src/solaris/classes/sun/font/NativeStrike.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/classes/sun/font/NativeStrike.java	Mon Nov 05 10:33:18 2012 -0500
@@ -32,7 +32,7 @@
 import java.awt.geom.Rectangle2D;
 import java.awt.geom.NoninvertibleTransformException;
 
- class NativeStrike extends PhysicalStrike {
+class NativeStrike extends PhysicalStrike {
 
      NativeFont nativeFont;
      int numGlyphs;
@@ -294,86 +294,3 @@
      }
 
 }
-
-/* Returned instead of a NativeStrike.
- * It can intercept any request it wants, but mostly
- * passes them on to its delegate strike. It is important that
- * it override all the inherited FontStrike methods to delegate them
- * appropriately.
- */
-
-class DelegateStrike extends NativeStrike {
-
-    private FontStrike delegateStrike;
-
-    DelegateStrike(NativeFont nativeFont, FontStrikeDesc desc,
-                   FontStrike delegate) {
-        super(nativeFont, desc);
-        this.delegateStrike = delegate;
-    }
-
-    /* We want the native font to be responsible for reporting the
-     * font metrics, even if it often delegates to another font.
-     * The code here isn't yet implementing exactly that. If the glyph
-     * transform was something native couldn't handle, there's no native
-     * context from which to obtain metrics. Need to revise this to obtain
-     * the metrics and transform them. But currently in such a case it
-     * gets the metrics from a different font - its glyph delegate font.
-     */
-   StrikeMetrics getFontMetrics() {
-       if (strikeMetrics == null) {
-           if (pScalerContext != 0) {
-               strikeMetrics = super.getFontMetrics();
-           }
-            if (strikeMetrics == null) {
-                strikeMetrics = delegateStrike.getFontMetrics();
-            }
-        }
-        return strikeMetrics;
-    }
-
-    void getGlyphImagePtrs(int[] glyphCodes, long[] images,int  len) {
-        delegateStrike.getGlyphImagePtrs(glyphCodes, images, len);
-    }
-
-    long getGlyphImagePtr(int glyphCode) {
-        return delegateStrike.getGlyphImagePtr(glyphCode);
-    }
-
-    void getGlyphImageBounds(int glyphCode,
-                             Point2D.Float pt, Rectangle result) {
-        delegateStrike.getGlyphImageBounds(glyphCode, pt, result);
-    }
-
-    Point2D.Float getGlyphMetrics(int glyphCode) {
-        return delegateStrike.getGlyphMetrics(glyphCode);
-    }
-
-    float getGlyphAdvance(int glyphCode) {
-        return delegateStrike.getGlyphAdvance(glyphCode);
-    }
-
-     Point2D.Float getCharMetrics(char ch) {
-        return delegateStrike.getCharMetrics(ch);
-    }
-
-    float getCodePointAdvance(int cp) {
-        if (cp < 0 || cp >= 0x10000) {
-            cp = 0xffff;
-        }
-        return delegateStrike.getGlyphAdvance(cp);
-    }
-
-    Rectangle2D.Float getGlyphOutlineBounds(int glyphCode) {
-        return delegateStrike.getGlyphOutlineBounds(glyphCode);
-    }
-
-    GeneralPath getGlyphOutline(int glyphCode, float x, float y) {
-        return delegateStrike.getGlyphOutline(glyphCode, x, y);
-    }
-
-    GeneralPath getGlyphVectorOutline(int[] glyphs, float x, float y) {
-        return delegateStrike.getGlyphVectorOutline(glyphs, x, y);
-    }
-
-}
--- a/src/solaris/classes/sun/java2d/jules/JulesAATileGenerator.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/classes/sun/java2d/jules/JulesAATileGenerator.java	Mon Nov 05 10:33:18 2012 -0500
@@ -326,24 +326,3 @@
         return tiledTrapArray[index];
     }
 }
-
-class TileTrapContainer {
-    int tileAlpha;
-    GrowableIntArray traps;
-
-    public TileTrapContainer(GrowableIntArray traps) {
-        this.traps = traps;
-    }
-
-    public void setTileAlpha(int tileAlpha) {
-        this.tileAlpha = tileAlpha;
-    }
-
-    public int getTileAlpha() {
-        return tileAlpha;
-    }
-
-    public GrowableIntArray getTraps() {
-        return traps;
-    }
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/solaris/classes/sun/java2d/jules/TileTrapContainer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,49 @@
+/*
+ * Copyright (c) 2010, 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.java2d.jules;
+
+import sun.java2d.xr.GrowableIntArray;
+
+class TileTrapContainer {
+    int tileAlpha;
+    GrowableIntArray traps;
+
+    public TileTrapContainer(GrowableIntArray traps) {
+        this.traps = traps;
+    }
+
+    public void setTileAlpha(int tileAlpha) {
+        this.tileAlpha = tileAlpha;
+    }
+
+    public int getTileAlpha() {
+        return tileAlpha;
+    }
+
+    public GrowableIntArray getTraps() {
+        return traps;
+    }
+}
--- a/src/solaris/native/com/sun/security/auth/module/Unix.c	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/native/com/sun/security/auth/module/Unix.c	Mon Nov 05 10:33:18 2012 -0500
@@ -47,83 +47,53 @@
     jsize numSuppGroups = getgroups(0, NULL);
     gid_t *groups = (gid_t *)calloc(numSuppGroups, sizeof(gid_t));
 
-    jfieldID fid;
+    jfieldID userNameID;
+    jfieldID userID;
+    jfieldID groupID;
+    jfieldID supplementaryGroupID;
+
     jstring jstr;
     jlongArray jgroups;
     jlong *jgroupsAsArray;
     jclass cls = (*env)->GetObjectClass(env, obj);
 
     memset(pwd_buf, 0, sizeof(pwd_buf));
+
     if (getpwuid_r(getuid(), &resbuf, pwd_buf, sizeof(pwd_buf), &pwd) == 0 &&
         pwd != NULL &&
         getgroups(numSuppGroups, groups) != -1) {
 
-        /*
-         * set username
-         */
-        fid = (*env)->GetFieldID(env, cls, "username", "Ljava/lang/String;");
-        if (fid == 0) {
-            jclass newExcCls =
-                (*env)->FindClass(env, "java/lang/IllegalArgumentException");
-            if (newExcCls == 0) {
-                /* Unable to find the new exception class, give up. */
-                return;
-            }
-            (*env)->ThrowNew(env, newExcCls, "invalid field: username");
-        }
-        jstr = (*env)->NewStringUTF(env, pwd->pw_name);
-        (*env)->SetObjectField(env, obj, fid, jstr);
+        userNameID = (*env)->GetFieldID(env, cls, "username", "Ljava/lang/String;");
+        if (userNameID == 0)
+            goto cleanUpAndReturn;
+
+        userID = (*env)->GetFieldID(env, cls, "uid", "J");
+        if (userID == 0)
+            goto cleanUpAndReturn;
 
-        /*
-         * set uid
-         */
-        fid = (*env)->GetFieldID(env, cls, "uid", "J");
-        if (fid == 0) {
-            jclass newExcCls =
-                (*env)->FindClass(env, "java/lang/IllegalArgumentException");
-            if (newExcCls == 0) {
-                /* Unable to find the new exception class, give up. */
-                return;
-            }
-            (*env)->ThrowNew(env, newExcCls, "invalid field: username");
-        }
-        (*env)->SetLongField(env, obj, fid, pwd->pw_uid);
+        groupID = (*env)->GetFieldID(env, cls, "gid", "J");
+        if (groupID == 0)
+            goto cleanUpAndReturn;
 
-        /*
-         * set gid
-         */
-        fid = (*env)->GetFieldID(env, cls, "gid", "J");
-        if (fid == 0) {
-            jclass newExcCls =
-                (*env)->FindClass(env, "java/lang/IllegalArgumentException");
-            if (newExcCls == 0) {
-                /* Unable to find the new exception class, give up. */
-                return;
-            }
-            (*env)->ThrowNew(env, newExcCls, "invalid field: username");
-        }
-        (*env)->SetLongField(env, obj, fid, pwd->pw_gid);
+        supplementaryGroupID = (*env)->GetFieldID(env, cls, "groups", "[J");
+        if (supplementaryGroupID == 0)
+            goto cleanUpAndReturn;
 
-        /*
-         * set supplementary groups
-         */
-        fid = (*env)->GetFieldID(env, cls, "groups", "[J");
-        if (fid == 0) {
-            jclass newExcCls =
-                (*env)->FindClass(env, "java/lang/IllegalArgumentException");
-            if (newExcCls == 0) {
-                /* Unable to find the new exception class, give up. */
-                return;
-            }
-            (*env)->ThrowNew(env, newExcCls, "invalid field: username");
-        }
+        jstr = (*env)->NewStringUTF(env, pwd->pw_name);
+        (*env)->SetObjectField(env, obj, userNameID, jstr);
+
+        (*env)->SetLongField(env, obj, userID, pwd->pw_uid);
+
+        (*env)->SetLongField(env, obj, groupID, pwd->pw_gid);
 
         jgroups = (*env)->NewLongArray(env, numSuppGroups);
         jgroupsAsArray = (*env)->GetLongArrayElements(env, jgroups, 0);
         for (i = 0; i < numSuppGroups; i++)
             jgroupsAsArray[i] = groups[i];
         (*env)->ReleaseLongArrayElements(env, jgroups, jgroupsAsArray, 0);
-        (*env)->SetObjectField(env, obj, fid, jgroups);
+        (*env)->SetObjectField(env, obj, supplementaryGroupID, jgroups);
     }
+cleanUpAndReturn:
+    free(groups);
     return;
 }
--- a/src/solaris/native/java/io/FileSystem_md.c	Mon Nov 05 10:30:49 2012 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,35 +0,0 @@
-/*
- * Copyright (c) 1998, 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 "jni.h"
-#include "jni_util.h"
-#include "java_io_FileSystem.h"
-
-
-JNIEXPORT jobject JNICALL
-Java_java_io_FileSystem_getFileSystem(JNIEnv *env, jclass ignored)
-{
-    return JNU_NewObjectByName(env, "java/io/UnixFileSystem", "()V");
-}
--- a/src/solaris/native/java/net/PlainDatagramSocketImpl.c	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/native/java/net/PlainDatagramSocketImpl.c	Mon Nov 05 10:33:18 2012 -0500
@@ -1318,10 +1318,8 @@
                                                       jobject value) {
     int fd;
     int level, optname, optlen;
-    union {
-        int i;
-        char c;
-    } optval;
+    int optval;
+    optlen = sizeof(int);
 
     /*
      * Check that socket hasn't been closed
@@ -1381,8 +1379,7 @@
                 fid =  (*env)->GetFieldID(env, cls, "value", "I");
                 CHECK_NULL(fid);
 
-                optval.i = (*env)->GetIntField(env, value, fid);
-                optlen = sizeof(optval.i);
+                optval = (*env)->GetIntField(env, value, fid);
                 break;
             }
 
@@ -1401,8 +1398,7 @@
                 on = (*env)->GetBooleanField(env, value, fid);
 
                 /* SO_REUSEADDR or SO_BROADCAST */
-                optval.i = (on ? 1 : 0);
-                optlen = sizeof(optval.i);
+                optval = (on ? 1 : 0);
 
                 break;
             }
--- a/src/solaris/native/java/net/net_util_md.c	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/native/java/net/net_util_md.c	Mon Nov 05 10:33:18 2012 -0500
@@ -546,6 +546,7 @@
     char dest_str[40];
     struct in6_addr dest_addr;
     char device[16];
+    struct loopback_route *loRoutesTemp;
 
     if (loRoutes != 0) {
         free (loRoutes);
@@ -606,11 +607,15 @@
             continue;
         } else {
             if (nRoutes == loRoutes_size) {
-                loRoutes = realloc (loRoutes, loRoutes_size *
-                                sizeof (struct loopback_route) * 2);
-                if (loRoutes == 0) {
-                    return ;
+                loRoutesTemp = realloc (loRoutes, loRoutes_size *
+                                        sizeof (struct loopback_route) * 2);
+
+                if (loRoutesTemp == 0) {
+                    free(loRoutes);
+                    fclose (f);
+                    return;
                 }
+                loRoutes=loRoutesTemp;
                 loRoutes_size *= 2;
             }
             memcpy (&loRoutes[nRoutes].addr,&dest_addr,sizeof(struct in6_addr));
--- a/src/solaris/native/sun/awt/awt_GraphicsEnv.c	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/solaris/native/sun/awt/awt_GraphicsEnv.c	Mon Nov 05 10:33:18 2012 -0500
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 1997, 2012, 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
@@ -753,7 +753,7 @@
                      sizeof(errmsg),
                      "Can't connect to X11 window server using '%s' as the value of the DISPLAY variable.",
                      (getenv("DISPLAY") == NULL) ? ":0.0" : getenv("DISPLAY"));
-        JNU_ThrowInternalError(env, errmsg);
+        JNU_ThrowByName(env, "java/awt/AWTError", errmsg);
         return NULL;
     }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/windows/classes/java/io/DefaultFileSystem.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2012, 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 java.io;
+
+/**
+ *
+ * @since 1.8
+ */
+class DefaultFileSystem {
+
+    /**
+     * Return the FileSystem object for Windows platform.
+     */
+    public static FileSystem getFileSystem() {
+        return new WinNTFileSystem();
+    }
+}
--- a/src/windows/classes/sun/awt/shell/Win32ShellFolder2.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/windows/classes/sun/awt/shell/Win32ShellFolder2.java	Mon Nov 05 10:33:18 2012 -0500
@@ -1099,7 +1099,7 @@
                                     ? SwingConstants.CENTER
                                     : SwingConstants.LEADING);
 
-                            column.setComparator(new ColumnComparator(getIShellFolder(), i));
+                            column.setComparator(new ColumnComparator(Win32ShellFolder2.this, i));
 
                             notNullColumns.add(column);
                         }
@@ -1135,7 +1135,7 @@
         // synchronize the whole code of the sort method once
         invoke(new Callable<Void>() {
             public Void call() {
-                Collections.sort(files, new ColumnComparator(getIShellFolder(), 0));
+                Collections.sort(files, new ColumnComparator(Win32ShellFolder2.this, 0));
 
                 return null;
             }
@@ -1143,12 +1143,12 @@
     }
 
     private static class ColumnComparator implements Comparator<File> {
-        private final long parentIShellFolder;
+        private final Win32ShellFolder2 shellFolder;
 
         private final int columnIdx;
 
-        public ColumnComparator(long parentIShellFolder, int columnIdx) {
-            this.parentIShellFolder = parentIShellFolder;
+        public ColumnComparator(Win32ShellFolder2 shellFolder, int columnIdx) {
+            this.shellFolder = shellFolder;
             this.columnIdx = columnIdx;
         }
 
@@ -1159,7 +1159,7 @@
                     if (o instanceof Win32ShellFolder2
                         && o1 instanceof Win32ShellFolder2) {
                         // delegates comparison to native method
-                        return compareIDsByColumn(parentIShellFolder,
+                        return compareIDsByColumn(shellFolder.getIShellFolder(),
                             ((Win32ShellFolder2) o).getRelativePIDL(),
                             ((Win32ShellFolder2) o1).getRelativePIDL(),
                             columnIdx);
--- a/src/windows/native/java/io/FileSystem_md.c	Mon Nov 05 10:30:49 2012 -0500
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,34 +0,0 @@
-/*
- * Copyright (c) 1998, 2012, 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 "jni_util.h"
-
-JNIEXPORT jobject JNICALL
-Java_java_io_FileSystem_getFileSystem(JNIEnv *env, jclass ignored)
-{
-    return JNU_NewObjectByName(env, "java/io/WinNTFileSystem", "()V");
-}
--- a/src/windows/native/sun/windows/awt_Window.cpp	Mon Nov 05 10:30:49 2012 -0500
+++ b/src/windows/native/sun/windows/awt_Window.cpp	Mon Nov 05 10:33:18 2012 -0500
@@ -1559,21 +1559,8 @@
 
 BOOL AwtWindow::AwtSetActiveWindow(BOOL isMouseEventCause, UINT hittest)
 {
-    // Fix for 6458497.
-    // Retreat if current foreground window is out of both our and embedder process.
-    // The exception is when activation is requested due to a mouse event.
-    if (!isMouseEventCause) {
-        HWND fgWindow = ::GetForegroundWindow();
-        if (NULL != fgWindow) {
-            DWORD fgProcessID;
-            ::GetWindowThreadProcessId(fgWindow, &fgProcessID);
-            if (fgProcessID != ::GetCurrentProcessId()
-                && !AwtToolkit::GetInstance().IsEmbedderProcessId(fgProcessID))
-            {
-                return FALSE;
-            }
-        }
-    }
+    // We used to reject non mouse window activation if our app wasn't active.
+    // This code since has been removed as the fix for 7185280
 
     HWND proxyContainerHWnd = GetProxyToplevelContainer();
     HWND proxyHWnd = GetProxyFocusOwner();
--- a/test/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -508,6 +508,7 @@
 	  javax/sql \
           javax/smartcardio \
 	  javax/xml/ws com/sun/internal/ws \
+	  jdk/asm \
 	  com/sun/org/apache/xerces \
           com/sun/corba \
 	  com/sun/servicetag \
--- a/test/ProblemList.txt	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/ProblemList.txt	Mon Nov 05 10:33:18 2012 -0500
@@ -143,6 +143,11 @@
 java/lang/management/MemoryMXBean/MemoryTest.java		generic-all
 java/lang/management/MemoryMXBean/MemoryTestAllGC.sh		generic-all
 
+# Exclude until hotspot/jdk repos are sync'd w.r.t. JAVA_MAX_SUPPORTED_VERSION
+# Needed when hotspot fix 7054345 is present.  Remove when the JDK source is 
+# updated accordingly.
+java/lang/System/Versions.java   generic-all
+
 ############################################################################
 
 # jdk_management
@@ -314,6 +319,9 @@
 sun/security/tools/keytool/selfissued.sh                        solaris-all
 sun/security/tools/keytool/standard.sh                          solaris-all
 
+# 8000439: NPG: REGRESSION : sun/security/krb5/auto/MaxRetries.java fails with timeout
+sun/security/krb5/auto/MaxRetries.java                          solaris-sparcv9
+
 ############################################################################
 
 # jdk_sound
--- a/test/java/awt/Frame/7024749/bug7024749.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/awt/Frame/7024749/bug7024749.java	Mon Nov 05 10:33:18 2012 -0500
@@ -25,7 +25,7 @@
  * @test
  * @bug 7024749
  * @summary JDK7 b131---a crash in: Java_sun_awt_windows_ThemeReader_isGetThemeTransitionDurationDefined+0x75
- * @library ../../../regtesthelpers
+ * @library ../../regtesthelpers
  * @build Util
  * @author Oleg Pekhovskiy: area=awt.toplevel
    @run main bug7024749
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/awt/GraphicsConfiguration/NormalizingTransformTest/NormalizingTransformTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2012, 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 6373505
+ * @summary Tests that the result of Toolkit.getScreenResolution() is
+ * consistent with GraphicsConfiguration.getNormalizingTransform().
+ * @author Dmitri.Trembovetski@Sun.COM: area=GraphicsConfiguration
+ * @run main NormalizingTransformTest
+ */
+
+import java.awt.GraphicsConfiguration;
+import java.awt.GraphicsEnvironment;
+import java.awt.Toolkit;
+import java.awt.geom.AffineTransform;
+
+public class NormalizingTransformTest {
+
+    public static void main(String[] args) {
+        GraphicsConfiguration gc =
+            GraphicsEnvironment.getLocalGraphicsEnvironment().
+                getDefaultScreenDevice().getDefaultConfiguration();
+        AffineTransform normTransform = gc.getNormalizingTransform();
+        int dpiX = Toolkit.getDefaultToolkit().getScreenResolution();
+        int normDpiX = (int)(normTransform.getScaleX() * 72.0);
+        if (dpiX != normDpiX) {
+            throw new RuntimeException(
+                "Test FAILED. Toolkit.getScreenResolution()=" + dpiX +
+                " GraphicsConfiguration.getNormalizingTransform()="+normDpiX);
+        }
+        System.out.println("Test PASSED. DPI="+normDpiX);
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/awt/Toolkit/BadDisplayTest/BadDisplayTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,48 @@
+/*
+ * Copyright (c) 2012, 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
+ * @summary Test that Toolkit.getDefaultToolkit throws AWTError exception if bad DISPLAY variable was set
+ * @bug 6818083
+ *
+ * @run shell/timeout=240 BadDisplayTest.sh
+ */
+
+import java.awt.*;
+
+public class BadDisplayTest{
+   public static void main(String[] args) {
+
+        Throwable th = null;
+        try {
+            Toolkit.getDefaultToolkit();
+        } catch (Throwable x) {
+            th = x;
+        }
+        if ( !(th instanceof AWTError)) {
+            System.exit(1);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/awt/Toolkit/BadDisplayTest/BadDisplayTest.sh	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,42 @@
+# Copyright (c) 2012, 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.
+
+${TESTJAVA}/bin/javac -cp ${TESTSRC} -d . ${TESTSRC}/BadDisplayTest.java
+
+
+export DISPLAY=
+
+OS=`uname -s`
+case "$OS" in
+  SunOS )
+    ${TESTJAVA}/bin/java BadDisplayTest
+    ;;
+  Linux )
+    ${TESTJAVA}/bin/java BadDisplayTest
+     ;;
+  * )
+    echo "Unsupported System: ${OS}"
+    exit 0;
+    ;;
+esac
+
+exit $?
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/StringBuffer/AppendStringBuilder.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2012, 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 6206780
+ * @summary Test StringBuffer.append(StringBuilder);
+ */
+
+import java.util.Random;
+
+public class AppendStringBuilder {
+    private static Random generator = new Random();
+
+    public static void main(String[] args) throws Exception {
+        for (int i=0; i<1000; i++) {
+            StringBuilder sb1 = generateTestBuilder(10, 100);
+            StringBuilder sb2 = generateTestBuilder(10, 100);
+            StringBuilder sb3 = generateTestBuilder(10, 100);
+            String s1 = sb1.toString();
+            String s2 = sb2.toString();
+            String s3 = sb3.toString();
+
+            String concatResult = new String(s1+s2+s3);
+
+            StringBuffer test = new StringBuffer();
+            test.append(sb1);
+            test.append(sb2);
+            test.append(sb3);
+
+            if (!test.toString().equals(concatResult))
+                throw new RuntimeException("StringBuffer.append failure");
+        }
+    }
+
+    private static int getRandomIndex(int constraint1, int constraint2) {
+        int range = constraint2 - constraint1;
+        int x = generator.nextInt(range);
+        return constraint1 + x;
+    }
+
+    private static StringBuilder generateTestBuilder(int min, int max) {
+        StringBuilder aNewStringBuilder = new StringBuilder(120);
+        int aNewLength = getRandomIndex(min, max);
+        for(int y=0; y<aNewLength; y++) {
+            int achar = generator.nextInt(30)+30;
+            char test = (char)(achar);
+            aNewStringBuilder.append(test);
+        }
+        return aNewStringBuilder;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/StringBuffer/BufferForwarding.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,242 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+/**
+ * @test
+ * @bug 6206780
+ * @summary  Test forwarding of methods to super in StringBuffer
+ * @author Jim Gish <jim.gish@oracle.com>
+ */
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class BufferForwarding {
+    private final static String A_STRING_BUFFER_VAL = "aStringBuffer";
+    private final static String A_STRING_BUILDER_VAL = "aStringBuilder";
+    private final static String A_STRING_VAL = "aString";
+    private final static String NON_EMPTY_VAL = "NonEmpty";
+
+    public BufferForwarding() {
+        System.out.println( "Starting BufferForwarding");
+    }
+
+    public static void main(String... args) {
+        new BufferForwarding().executeTestMethods();
+    }
+
+    public void executeTestMethods() {
+        appendCharSequence();
+        indexOfString();
+        indexOfStringIntNull();
+        indexOfStringNull();
+        indexOfStringint();
+        insertintCharSequence();
+        insertintObject();
+        insertintboolean();
+        insertintchar();
+        insertintdouble();
+        insertintfloat();
+        insertintint();
+        insertintlong();
+        lastIndexOfString();
+        lastIndexOfStringint();
+    }
+
+    public void appendCharSequence() {
+        // three different flavors of CharSequence
+        CharSequence aString = A_STRING_VAL;
+        CharSequence aStringBuilder = new StringBuilder(A_STRING_BUILDER_VAL);
+        CharSequence aStringBuffer = new StringBuffer(A_STRING_BUFFER_VAL);
+
+        assertEquals( /*actual*/ new StringBuilder().append(aString).toString(), /*expected*/ A_STRING_VAL );
+        assertEquals( new StringBuilder().append(aStringBuilder).toString(), A_STRING_BUILDER_VAL );
+        assertEquals( new StringBuilder().append(aStringBuffer).toString(), A_STRING_BUFFER_VAL );
+
+        assertEquals( /*actual*/ new StringBuilder(NON_EMPTY_VAL).append(aString).toString(), NON_EMPTY_VAL+A_STRING_VAL );
+        assertEquals( new StringBuilder(NON_EMPTY_VAL).append(aStringBuilder).toString(), NON_EMPTY_VAL+A_STRING_BUILDER_VAL );
+        assertEquals( new StringBuilder(NON_EMPTY_VAL).append(aStringBuffer).toString(), NON_EMPTY_VAL+A_STRING_BUFFER_VAL );
+    }
+
+    void indexOfString() {
+        StringBuffer sb = new StringBuffer("xyz");
+        assertEquals( sb.indexOf("y"), 1 );
+        assertEquals( sb.indexOf("not found"), -1 );
+    }
+
+
+    public void indexOfStringint() {
+        StringBuffer sb = new StringBuffer("xyyz");
+        assertEquals( sb.indexOf("y",0), 1 );
+        assertEquals( sb.indexOf("y",1), 1 );
+        assertEquals( sb.indexOf("y",2), 2 );
+        assertEquals( sb.indexOf("not found"), -1 );
+    }
+
+
+    public void indexOfStringIntNull() {
+        StringBuffer sb = new StringBuffer();
+        // should be NPE if null passed
+        try {
+            sb.indexOf(null,1);
+            throw new RuntimeException("Test failed: should have thrown NPE");
+        } catch (NullPointerException npe) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown NPE. Instead threw "
+                    + t);
+        }
+    }
+
+
+    public void indexOfStringNull() {
+        StringBuffer sb = new StringBuffer();
+
+        // should be NPE if null passed
+        try {
+            sb.indexOf(null);
+            throw new RuntimeException("Test failed: should have thrown NPE");
+        } catch (NullPointerException npe) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown NPE. Instead threw "
+                    + t);
+        }
+    }
+
+
+    public void insertintboolean() {
+        boolean b = true;
+        StringBuffer sb = new StringBuffer("012345");
+        assertEquals( sb.insert( 2, b).toString(), "01true2345");
+    }
+
+
+    public void insertintchar() {
+        char c = 'C';
+        StringBuffer sb = new StringBuffer("012345");
+        assertEquals( sb.insert( 2, c ).toString(), "01C2345");
+    }
+
+
+    public void insertintCharSequence() {
+        final String initString = "012345";
+        // three different flavors of CharSequence
+        CharSequence aString = A_STRING_VAL;
+        CharSequence aStringBuilder = new StringBuilder(A_STRING_BUILDER_VAL);
+        CharSequence aStringBuffer = new StringBuffer(A_STRING_BUFFER_VAL);
+
+        assertEquals( new StringBuffer(initString).insert(2, aString).toString(), "01"+A_STRING_VAL+"2345" );
+
+        assertEquals( new StringBuffer(initString).insert(2, aStringBuilder).toString(), "01"+A_STRING_BUILDER_VAL+"2345" );
+
+        assertEquals( new StringBuffer(initString).insert(2, aStringBuffer).toString(), "01"+A_STRING_BUFFER_VAL+"2345" );
+
+        try {
+            new StringBuffer(initString).insert(7, aString);
+            throw new RuntimeException("Test failed: should have thrown IndexOutOfBoundsException");
+        } catch (IndexOutOfBoundsException soob) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown IndexOutOfBoundsException, but instead threw " + t.getMessage());
+
+        }
+    }
+
+    public void insertintdouble() {
+        double d = 99d;
+        StringBuffer sb = new StringBuffer("012345");
+        assertEquals( sb.insert( 2, d ).toString(), "0199.02345");    }
+
+
+    public void insertintfloat() {
+        float f = 99.0f;
+        StringBuffer sb = new StringBuffer("012345");
+        assertEquals( sb.insert( 2, f ).toString(), "0199.02345");    }
+
+
+    public void insertintint() {
+        int i = 99;
+        StringBuffer sb = new StringBuffer("012345");
+        assertEquals( sb.insert( 2, i ).toString(), "01992345");
+    }
+
+
+    public void insertintlong() {
+        long l = 99;
+        StringBuffer sb = new StringBuffer("012345");
+        assertEquals( sb.insert( 2, l ).toString(), "01992345");    }
+
+    public void insertintObject() {
+        StringBuffer sb = new StringBuffer("012345");
+        List<String> ls = new ArrayList<String>();
+        ls.add("A"); ls.add("B");
+        String lsString = ls.toString();
+        assertEquals( sb.insert(2, ls).toString(), "01"+lsString+"2345");
+
+        try {
+            sb.insert(sb.length()+1, ls);
+            throw new RuntimeException("Test failed: should have thrown StringIndexOutOfBoundsException");
+        } catch (StringIndexOutOfBoundsException soob) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown StringIndexOutOfBoundsException, but instead threw:"
+                    + t);
+
+        }
+    }
+
+
+
+    public void lastIndexOfString() {
+        String xyz = "xyz";
+        String xyz3 = "xyzxyzxyz";
+        StringBuffer sb = new StringBuffer(xyz3);
+        int pos = sb.lastIndexOf("xyz");
+        assertEquals( pos, 2*xyz.length() );
+    }
+
+    public void lastIndexOfStringint() {
+        StringBuffer sb = new StringBuffer("xyzxyzxyz");
+        int pos = sb.lastIndexOf("xyz",5);
+        assertEquals( pos, 3 );
+        pos = sb.lastIndexOf("xyz", 6);
+        assertEquals( pos, 6 );
+    }
+
+    public void assertEquals( String actual, String expected) {
+        if (!actual.equals( expected )) {
+            throw new RuntimeException( "Test failed: actual = '" + actual +
+                    "', expected = '" + expected + "'");
+        }
+    }
+
+    public void assertEquals( int actual, int expected) {
+        if (actual != expected) {
+            throw new RuntimeException( "Test failed: actual = '" + actual +
+                    "', expected = '" + expected + "'");
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/StringBuffer/TestSynchronization.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,315 @@
+/*
+ * Copyright (c) 2012 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 6206780
+ * @summary Test that all public unsynchronized methods of StringBuffer are either directly or indirectly synchronized
+ */
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+import java.lang.reflect.Method;
+import java.lang.reflect.Modifier;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * TestSynchronization tests whether synchronized methods calls on an object
+ * result in synchronized calls. Note that this may not test all cases desired.
+ * It only tests whether some synchronization has occurred on the object during
+ * the call chain, and can't tell whether the object was locked across all
+ * operations that have been performed on the object.
+ */
+public class TestSynchronization {
+
+    /**
+     * Define parameters used in methods of StringBuffer - admittedly a bit of
+     * hack but 'purpose-built' for StringBuffer. Something more general could
+     * probably be developed if the test needs to be more widely adopted.
+     * <p/>
+     * boolean char char[] int double float long Object CharSequence String
+     * StringBuffer StringBuilder
+     * <p/>
+     */
+    private static final boolean BOOLEAN_VAL = true;
+    private static final char CHAR_VAL = 'x';
+    private static final char[] CHAR_ARRAY_VAL = {'c', 'h', 'a', 'r', 'a', 'r',
+        'r', 'a', 'y'};
+    private static final int INT_VAL = 1;
+    private static final double DOUBLE_VAL = 1.0d;
+    private static final float FLOAT_VAL = 1.0f;
+    private static final long LONG_VAL = 1L;
+    private static final Object OBJECT_VAL = new Object();
+    private static final String STRING_VAL = "String value";
+    private static final StringBuilder STRING_BUILDER_VAL =
+            new StringBuilder("StringBuilder value");
+    private static final StringBuffer STRING_BUFFER_VAL =
+            new StringBuffer("StringBuffer value");
+    private static final CharSequence[] CHAR_SEQUENCE_VAL = {STRING_VAL,
+        STRING_BUILDER_VAL, STRING_BUFFER_VAL};
+
+    public static void main(String... args) throws Exception {
+        // First, test the tester
+        testClass(MyTestClass.class, /*
+                 * self-test
+                 */ true);
+        // Finally, test StringBuffer
+        testClass(StringBuffer.class, /*
+                 * self-test
+                 */ false);
+    }
+
+    /**
+     * Test all the public, unsynchronized methods of the given class. If
+     * isSelfTest is true, this is a self-test to ensure that the test program
+     * itself is working correctly. Should help ensure correctness of this
+     * program if it changes.
+     * <p/>
+     * @param aClass - the class to test
+     * @param isSelfTest - true if this is the special self-test class
+     * @throws SecurityException
+     */
+    private static void testClass(Class<?> aClass, boolean isSelfTest) throws
+            Exception {
+        // Get all unsynchronized public methods via reflection.  We don't need
+        // to test synchronized methods.  By definition. they are already doing
+        // the right thing.
+        List<Method> methods = Arrays.asList(aClass.getDeclaredMethods());
+        for (Method m : methods) {
+            int modifiers = m.getModifiers();
+            if (Modifier.isPublic(modifiers)
+                    && !Modifier.isSynchronized(modifiers)) {
+                try {
+                    testMethod(aClass, m);
+                } catch (TestFailedException e) {
+                    if (isSelfTest) {
+                        String methodName = e.getMethod().getName();
+                        switch (methodName) {
+                            case "should_pass":
+                                throw new RuntimeException(
+                                        "Test failed: self-test failed.  The 'should_pass' method did not pass the synchronization test. Check the test code.");
+                            case "should_fail":
+                                break;
+                            default:
+                                throw new RuntimeException(
+                                        "Test failed: something is amiss with the test. A TestFailedException was generated on a call to "
+                                        + methodName + " which we didn't expect to test in the first place.");
+                        }
+                    } else {
+                        throw new RuntimeException("Test failed: the method "
+                                + e.getMethod().toString()
+                                + " should be synchronized, but isn't.");
+                    }
+                }
+            }
+        }
+    }
+
+    private static void invokeMethod(Class<?> aClass, final Method m,
+            final Object[] args) throws TestFailedException, Exception {
+        //System.out.println( "Invoking " + m.toString() + " with parameters " + Arrays.toString(args));
+        final Constructor<?> objConstructor;
+        Object obj = null;
+
+        objConstructor = aClass.getConstructor(String.class);
+        obj = objConstructor.newInstance("LeftPalindrome-emordnilaP-thgiR");
+
+        // test method m for synchronization
+        if (!isSynchronized(m, obj, args)) {
+            throw new TestFailedException(m);
+        }
+    }
+
+    private static void testMethod(Class<?> aClass, Method m) throws
+            Exception {
+        /*
+         * Construct call with arguments of the correct type. Note that the
+         * values are somewhat irrelevant. If the call actually succeeds, it
+         * means we aren't synchronized and the test has failed.
+         */
+        Class<?>[] pTypes = m.getParameterTypes();
+        List<Integer> charSequenceArgs = new ArrayList<>();
+        Object[] args = new Object[pTypes.length];
+        for (int i = 0; i < pTypes.length; i++) {
+            // determine the type and create the corresponding actual argument
+            Class<?> pType = pTypes[i];
+            if (pType.equals(boolean.class)) {
+                args[i] = BOOLEAN_VAL;
+            } else if (pType.equals(char.class)) {
+                args[i] = CHAR_VAL;
+            } else if (pType.equals(int.class)) {
+                args[i] = INT_VAL;
+            } else if (pType.equals(double.class)) {
+                args[i] = DOUBLE_VAL;
+            } else if (pType.equals(float.class)) {
+                args[i] = FLOAT_VAL;
+            } else if (pType.equals(long.class)) {
+                args[i] = LONG_VAL;
+            } else if (pType.equals(Object.class)) {
+                args[i] = OBJECT_VAL;
+            } else if (pType.equals(StringBuilder.class)) {
+                args[i] = STRING_BUILDER_VAL;
+            } else if (pType.equals(StringBuffer.class)) {
+                args[i] = STRING_BUFFER_VAL;
+            } else if (pType.equals(String.class)) {
+                args[i] = STRING_VAL;
+            } else if (pType.isArray() && pType.getComponentType().equals(char.class)) {
+                args[i] = CHAR_ARRAY_VAL;
+            } else if (pType.equals(CharSequence.class)) {
+                charSequenceArgs.add(new Integer(i));
+            } else {
+                throw new RuntimeException("Test Failed: not accounting for method call with parameter type of " + pType.getName() + " You must update the test.");
+            }
+        }
+        /*
+         * If there are no CharSequence args, we can simply invoke our method
+         * and test it
+         */
+        if (charSequenceArgs.isEmpty()) {
+            invokeMethod(aClass, m, args);
+        } else {
+            /*
+             * Iterate through the different CharSequence types and invoke the
+             * method for each type.
+             */
+            if (charSequenceArgs.size() > 1) {
+                throw new RuntimeException("Test Failed: the test cannot handle a method with multiple CharSequence arguments.  You must update the test to handle the method "
+                        + m.toString());
+            }
+            for (int j = 0; j < CHAR_SEQUENCE_VAL.length; j++) {
+                args[charSequenceArgs.get(0)] = CHAR_SEQUENCE_VAL[j];
+                invokeMethod(aClass, m, args);
+            }
+        }
+    }
+
+    @SuppressWarnings("serial")
+    private static class TestFailedException extends Exception {
+
+        final Method m;
+
+        public Method getMethod() {
+            return m;
+        }
+
+        public TestFailedException(Method m) {
+            this.m = m;
+        }
+    }
+
+    static class InvokeTask implements Runnable {
+
+        private final Method m;
+        private final Object target;
+        private final Object[] args;
+
+        InvokeTask(Method m, Object target, Object... args) {
+            this.m = m;
+            this.target = target;
+            this.args = args;
+        }
+
+        @Override
+        public void run() {
+            try {
+                m.invoke(target, args);
+            } catch (IllegalAccessException | IllegalArgumentException |
+                    InvocationTargetException e) {
+                e.printStackTrace();
+            }
+        }
+    }
+
+    /**
+     * isSynchronized tests whether the given method is synchronized or not by
+     * invoking it in a thread and testing the thread state after starting the
+     * thread
+     * <p/>
+     * @param m the method to test
+     * @param target the object the method is executed on
+     * @param args the arguments passed to the method
+     * @return true iff the method is synchronized
+     */
+    private static boolean isSynchronized(Method m, Object target,
+            Object... args) {
+        Thread t = new Thread(new InvokeTask(m, target, args));
+
+        Boolean isSynchronized = null;
+
+        synchronized (target) {
+            t.start();
+
+            while (isSynchronized == null) {
+                switch (t.getState()) {
+                    case NEW:
+                    case RUNNABLE:
+                    case WAITING:
+                    case TIMED_WAITING:
+                        Thread.yield();
+                        break;
+                    case BLOCKED:
+                        isSynchronized = true;
+                        break;
+                    case TERMINATED:
+                        isSynchronized = false;
+                        break;
+                }
+            }
+        }
+
+        try {
+            t.join();
+        } catch (InterruptedException ex) {
+            ex.printStackTrace();
+        }
+
+        return isSynchronized;
+    }
+
+    /*
+     * This class is used to test the synchronization tester above. It has a
+     * method, should_pass, that is unsynchronized but calls a synchronized
+     * method. It has another method, should_fail, which isn't synchronized and
+     * doesn't call a synchronized method. The former should pass and the latter
+     * should fail.
+     */
+    private static class MyTestClass {
+
+        @SuppressWarnings("unused")
+        public MyTestClass(String s) {
+        }
+
+        @SuppressWarnings("unused")
+        public void should_pass() {
+            // call sync method
+            sync_shouldnt_be_tested();
+        }
+
+        @SuppressWarnings("unused")
+        public void should_fail() {
+        }
+
+        public synchronized void sync_shouldnt_be_tested() {
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/StringBuilder/AppendStringBuffer.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,71 @@
+/*
+ * Copyright (c) 2012, 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 6206780
+ * @summary Test StringBuilder.append(StringBuffer);
+ */
+
+import java.util.Random;
+
+public class AppendStringBuffer {
+    private static Random generator = new Random();
+
+    public static void main(String[] args) throws Exception {
+        for (int i=0; i<1000; i++) {
+            StringBuffer sb1 = generateTestBuffer(10, 100);
+            StringBuffer sb2 = generateTestBuffer(10, 100);
+            StringBuffer sb3 = generateTestBuffer(10, 100);
+            String s1 = sb1.toString();
+            String s2 = sb2.toString();
+            String s3 = sb3.toString();
+
+            String concatResult = new String(s1+s2+s3);
+
+            StringBuilder test = new StringBuilder();
+            test.append(sb1);
+            test.append(sb2);
+            test.append(sb3);
+
+            if (!test.toString().equals(concatResult))
+                throw new RuntimeException("StringBuffer.append failure");
+        }
+    }
+
+    private static int getRandomIndex(int constraint1, int constraint2) {
+        int range = constraint2 - constraint1;
+        int x = generator.nextInt(range);
+        return constraint1 + x;
+    }
+
+    private static StringBuffer generateTestBuffer(int min, int max) {
+        StringBuffer aNewStringBuffer = new StringBuffer(120);
+        int aNewLength = getRandomIndex(min, max);
+        for(int y=0; y<aNewLength; y++) {
+            int achar = generator.nextInt(30)+30;
+            char test = (char)(achar);
+            aNewStringBuffer.append(test);
+        }
+        return aNewStringBuffer;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/StringBuilder/BuilderForwarding.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,269 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+
+/**
+ * @test
+ * @bug 6206780
+ * @summary  Test forwarding of methods to super in StringBuilder
+ * @author Jim Gish <jim.gish@oracle.com>
+ */
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class BuilderForwarding {
+    private final static String A_STRING_BUFFER_VAL = "aStringBuffer";
+    private final static String A_STRING_BUILDER_VAL = "aStringBuilder";
+    private final static String A_STRING_VAL = "aString";
+    private final static String NON_EMPTY_VAL = "NonEmpty";
+
+    public BuilderForwarding() {
+        System.out.println( "Starting BuilderForwarding");
+    }
+
+    public static void main(String... args) {
+        new BuilderForwarding().executeTestMethods();
+    }
+
+    public void executeTestMethods() {
+        appendCharSequence();
+        indexOfString();
+        indexOfStringIntNull();
+        indexOfStringNull();
+        indexOfStringint();
+        insertintCharSequence();
+        insertintObject();
+        insertintboolean();
+        insertintchar();
+        insertintdouble();
+        insertintfloat();
+        insertintint();
+        insertintlong();
+        lastIndexOfString();
+        lastIndexOfStringint();
+    }
+
+    public void appendCharSequence() {
+        // three different flavors of CharSequence
+        CharSequence aString = A_STRING_VAL;
+        CharSequence aStringBuilder = new StringBuilder(A_STRING_BUILDER_VAL);
+        CharSequence aStringBuffer = new StringBuffer(A_STRING_BUFFER_VAL);
+
+        assertEquals( /*actual*/ new StringBuilder().append(aString).toString(), /*expected*/ A_STRING_VAL );
+        assertEquals( new StringBuilder().append(aStringBuilder).toString(), A_STRING_BUILDER_VAL );
+        assertEquals( new StringBuilder().append(aStringBuffer).toString(), A_STRING_BUFFER_VAL );
+
+        assertEquals( /*actual*/ new StringBuilder(NON_EMPTY_VAL).append(aString).toString(), NON_EMPTY_VAL+A_STRING_VAL );
+        assertEquals( new StringBuilder(NON_EMPTY_VAL).append(aStringBuilder).toString(), NON_EMPTY_VAL+A_STRING_BUILDER_VAL );
+        assertEquals( new StringBuilder(NON_EMPTY_VAL).append(aStringBuffer).toString(), NON_EMPTY_VAL+A_STRING_BUFFER_VAL );
+    }
+
+
+    public void indexOfString() {
+        StringBuilder sb = new StringBuilder();
+        // should be NPE if null passed
+        try {
+
+            sb.indexOf(null);
+            throw new RuntimeException("Test failed: should have thrown NPE");
+
+
+        } catch (NullPointerException npe) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown NPE. Instead threw "
+                    + t);
+        }
+        sb = new StringBuilder("xyz");
+        assertEquals( sb.indexOf("y"), 1 );
+        assertEquals( sb.indexOf("not found"), -1 );
+    }
+
+
+    public void indexOfStringint() {
+        StringBuilder sb = new StringBuilder();
+        // should be NPE if null passed
+        try {
+            sb.indexOf(null,1);
+            throw new RuntimeException("Test failed: should have thrown NPE");
+        } catch (NullPointerException npe) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown NPE");
+        }
+        sb = new StringBuilder("xyyz");
+        assertEquals( sb.indexOf("y",0), 1 );
+        assertEquals( sb.indexOf("y",1), 1 );
+        assertEquals( sb.indexOf("y",2), 2 );
+        assertEquals( sb.indexOf("not found"), -1 );
+    }
+
+
+    public void indexOfStringIntNull() {
+        StringBuffer sb = new StringBuffer();
+        // should be NPE if null passed
+        try {
+            sb.indexOf(null,1);
+            throw new RuntimeException("Test failed: should have thrown NPE");
+        } catch (NullPointerException npe) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown NPE. Instead threw "
+                    + t);
+        }
+    }
+
+
+    public void indexOfStringNull() {
+        StringBuilder sb = new StringBuilder();
+
+        // should be NPE if null passed
+        try {
+            sb.indexOf(null);
+            throw new RuntimeException("Test failed: should have thrown NPE");
+        } catch (NullPointerException npe) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown NPE. Instead threw "
+                    + t);
+        }
+    }
+
+
+    public void insertintboolean() {
+        boolean b = true;
+        StringBuilder sb = new StringBuilder("012345");
+        assertEquals( sb.insert( 2, b).toString(), "01true2345");
+    }
+
+
+    public void insertintchar() {
+        char c = 'C';
+        StringBuilder sb = new StringBuilder("012345");
+        assertEquals( sb.insert( 2, c ).toString(), "01C2345");
+    }
+
+
+    public void insertintCharSequence() {
+        final String initString = "012345";
+        // three different flavors of CharSequence
+        CharSequence aString = A_STRING_VAL;
+        CharSequence aStringBuilder = new StringBuilder(A_STRING_BUILDER_VAL);
+        CharSequence aStringBuffer = new StringBuffer(A_STRING_BUFFER_VAL);
+
+        assertEquals( new StringBuilder(initString).insert(2, aString).toString(), "01"+A_STRING_VAL+"2345" );
+
+        assertEquals( new StringBuilder(initString).insert(2, aStringBuilder).toString(), "01"+A_STRING_BUILDER_VAL+"2345" );
+
+        assertEquals( new StringBuilder(initString).insert(2, aStringBuffer).toString(), "01"+A_STRING_BUFFER_VAL+"2345" );
+
+        try {
+            new StringBuilder(initString).insert(7, aString);
+            throw new RuntimeException("Test failed: should have thrown IndexOutOfBoundsException");
+        } catch (IndexOutOfBoundsException soob) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown IndexOutOfBoundsException, but instead threw " + t.getMessage());
+
+        }
+    }
+
+
+    public void insertintdouble() {
+        double d = 99d;
+        StringBuilder sb = new StringBuilder("012345");
+        assertEquals( sb.insert( 2, d ).toString(), "0199.02345");    }
+
+
+    public void insertintfloat() {
+        float f = 99.0f;
+        StringBuilder sb = new StringBuilder("012345");
+        assertEquals( sb.insert( 2, f ).toString(), "0199.02345");    }
+
+
+    public void insertintint() {
+        int i = 99;
+        StringBuilder sb = new StringBuilder("012345");
+        assertEquals( sb.insert( 2, i ).toString(), "01992345");
+    }
+
+
+    public void insertintlong() {
+        long l = 99;
+        StringBuilder sb = new StringBuilder("012345");
+        assertEquals( sb.insert( 2, l ).toString(), "01992345");    }
+
+
+    public void insertintObject() {
+        StringBuilder sb = new StringBuilder("012345");
+        List<String> ls = new ArrayList<String>();
+        ls.add("A"); ls.add("B");
+        String lsString = ls.toString();
+        assertEquals( sb.insert(2, ls).toString(), "01"+lsString+"2345");
+
+        try {
+            sb.insert(sb.length()+1, ls);
+            throw new RuntimeException("Test failed: should have thrown StringIndexOutOfBoundsException");
+        } catch (StringIndexOutOfBoundsException soob) {
+            // expected: passed
+        } catch (Throwable t) {
+            throw new RuntimeException("Test failed: should have thrown StringIndexOutOfBoundsException, but instead threw:"
+                    + t);
+        }
+    }
+
+
+    public void lastIndexOfString() {
+        String xyz = "xyz";
+        String xyz3 = "xyzxyzxyz";
+        StringBuilder sb = new StringBuilder(xyz3);
+        int pos = sb.lastIndexOf("xyz");
+        assertEquals( pos, 2*xyz.length() );
+    }
+
+
+    public void lastIndexOfStringint() {
+        StringBuilder sb = new StringBuilder("xyzxyzxyz");
+        int pos = sb.lastIndexOf("xyz",5);
+        assertEquals( pos, 3 );
+        pos = sb.lastIndexOf("xyz", 6);
+        assertEquals( pos, 6 );
+    }
+
+    public void assertEquals( String actual, String expected) {
+        if (!actual.equals( expected )) {
+            throw new RuntimeException( "Test failed: actual = '" + actual +
+                    "', expected = '" + expected + "'");
+        }
+    }
+
+    public void assertEquals( int actual, int expected) {
+        if (actual != expected) {
+            throw new RuntimeException( "Test failed: actual = '" + actual +
+                    "', expected = '" + expected + "'");
+        }
+    }
+}
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/invoke/7196190/ClassForNameTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,98 @@
+/*
+ * Copyright (c) 2012, 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 7196190
+ * @summary Improve method of handling MethodHandles
+ *
+ * @run main/othervm ClassForNameTest
+ */
+
+import java.lang.invoke.*;
+import java.lang.reflect.Method;
+import java.util.Arrays;
+
+public class ClassForNameTest {
+    final static String NAME = ClassForNameTest.class.getName();
+
+    public static void main(String[] args) throws Throwable {
+        {
+            final MethodType mt = MethodType.methodType(Class.class, String.class);
+            final MethodHandle mh = MethodHandles.lookup()
+                    .findStatic(Class.class, "forName", mt);
+
+            Class.forName(NAME);
+
+            mh.invoke(NAME);
+            mh.bindTo(NAME).invoke();
+            mh.invokeWithArguments(Arrays.asList(NAME));
+            mh.invokeWithArguments(NAME);
+            Class cls = (Class) mh.invokeExact(NAME);
+        }
+
+        {
+            final Method fnMethod = Class.class.getMethod("forName", String.class);
+            final MethodType mt = MethodType.methodType(Object.class, Object.class, Object[].class);
+            final MethodHandle mh = MethodHandles.lookup()
+                    .findVirtual(Method.class, "invoke", mt)
+                    .bindTo(fnMethod);
+
+            fnMethod.invoke(null, NAME);
+
+            mh.bindTo(null).bindTo(new Object[]{NAME}).invoke();
+            mh.invoke(null, new Object[]{NAME});
+            mh.invokeWithArguments(null, new Object[]{NAME});
+            mh.invokeWithArguments(Arrays.asList(null, new Object[]{NAME}));
+            Object obj = mh.invokeExact((Object) null, new Object[]{NAME});
+        }
+
+        {
+            final Method fnMethod = Class.class.getMethod("forName", String.class);
+            final MethodType mt = MethodType.methodType(Object.class, Object.class, Object[].class);
+
+            final MethodHandle mh = MethodHandles.lookup()
+                    .bind(fnMethod, "invoke", mt);
+
+            mh.bindTo(null).bindTo(new Object[]{NAME}).invoke();
+            mh.invoke(null, new Object[]{NAME});
+            mh.invokeWithArguments(null, NAME);
+            mh.invokeWithArguments(Arrays.asList(null, NAME));
+            Object obj = mh.invokeExact((Object) null, new Object[]{NAME});
+        }
+
+        {
+            final Method fnMethod = Class.class.getMethod("forName", String.class);
+            final MethodHandle mh = MethodHandles.lookup().unreflect(fnMethod);
+
+            mh.bindTo(NAME).invoke();
+            mh.invoke(NAME);
+            mh.invokeWithArguments(NAME);
+            mh.invokeWithArguments(Arrays.asList(NAME));
+            Class cls = (Class) mh.invokeExact(NAME);
+        }
+
+        System.out.println("TEST PASSED");
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/invoke/7196190/GetUnsafeTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,112 @@
+/*
+ * Copyright (c) 2012, 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 7196190
+ * @summary Improve method of handling MethodHandles
+ *
+ * @run main/othervm/policy=jtreg.security.policy/secure=java.lang.SecurityManager GetUnsafeTest
+ */
+
+import java.lang.invoke.*;
+import java.lang.reflect.Method;
+import java.util.Arrays;
+
+public class GetUnsafeTest {
+    final static String NAME = "sun.misc.Unsafe";
+
+    private static boolean isTestFailed = false;
+
+    private static void fail() {
+        isTestFailed = true;
+        try { throw new Exception(); } catch (Throwable e) {
+            StackTraceElement frame = e.getStackTrace()[1];
+            System.out.printf("Failed at %s:%d\n", frame.getFileName(), frame.getLineNumber());
+        }
+    }
+
+    public static void main(String[] args) throws Throwable {
+        {
+            final MethodType mt = MethodType.methodType(Class.class, String.class);
+            final MethodHandle mh = MethodHandles.lookup()
+                    .findStatic(Class.class, "forName", mt);
+
+            try { Class.forName(NAME);                         fail(); } catch (Throwable e) {}
+
+            try { mh.invoke(NAME);                             fail(); } catch (Throwable e) {}
+            try { mh.bindTo(NAME).invoke();                    fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(Arrays.asList(NAME)); fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(NAME);                fail(); } catch (Throwable e) {}
+            try { Class cls = (Class) mh.invokeExact(NAME);    fail(); } catch (Throwable e) {}
+        }
+
+        {
+            final Method fnMethod = Class.class.getMethod("forName", String.class);
+            final MethodType mt = MethodType.methodType(Object.class, Object.class, Object[].class);
+            final MethodHandle mh = MethodHandles.lookup()
+                    .findVirtual(Method.class, "invoke", mt)
+                    .bindTo(fnMethod);
+
+            try { fnMethod.invoke(null, NAME); fail(); } catch (Throwable e) {}
+
+            try { mh.bindTo(null).bindTo(new Object[]{NAME}).invoke();             fail(); } catch (Throwable e) {}
+            try { mh.invoke(null, new Object[]{NAME});                             fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(null, new Object[]{NAME});                fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(Arrays.asList(null, new Object[]{NAME})); fail(); } catch (Throwable e) {}
+            try { Object obj = mh.invokeExact((Object) null, new Object[]{NAME});  fail(); } catch (Throwable e) {}
+        }
+
+        {
+            final Method fnMethod = Class.class.getMethod("forName", String.class);
+            final MethodType mt = MethodType.methodType(Object.class, Object.class, Object[].class);
+
+            final MethodHandle mh = MethodHandles.lookup().bind(fnMethod, "invoke", mt);
+
+            try { mh.bindTo(null).bindTo(new Object[]{NAME}).invoke();            fail(); } catch (Throwable e) {}
+            try { mh.invoke(null, new Object[]{NAME});                            fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(null, NAME);                             fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(Arrays.asList(null, NAME));              fail(); } catch (Throwable e) {}
+            try { Object obj = mh.invokeExact((Object) null, new Object[]{NAME}); fail(); } catch (Throwable e) {}
+        }
+
+        {
+            final Method fnMethod = Class.class.getMethod("forName", String.class);
+            final MethodHandle mh = MethodHandles.lookup().unreflect(fnMethod);
+
+            try { mh.bindTo(NAME).invoke();                    fail(); } catch (Throwable e) {}
+            try { mh.invoke(NAME);                             fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(NAME);                fail(); } catch (Throwable e) {}
+            try { mh.invokeWithArguments(Arrays.asList(NAME)); fail(); } catch (Throwable e) {}
+            try { Class cls = (Class) mh.invokeExact(NAME);    fail(); } catch (Throwable e) {}
+        }
+
+        if (!isTestFailed) {
+            System.out.println("TEST PASSED");
+        } else {
+            System.out.println("TEST FAILED");
+            System.exit(1);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/invoke/7196190/MHProxyTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,181 @@
+/*
+ * Copyright (c) 2012, 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 7196190
+ * @summary Improve method of handling MethodHandles
+ *
+ * @run main/othervm MHProxyTest
+ */
+
+import java.lang.invoke.*;
+import java.security.*;
+import static java.lang.invoke.MethodHandles.*;
+import static java.lang.invoke.MethodType.*;
+
+public class MHProxyTest {
+    private static final Class<?> C_Unsafe;
+    private static final MethodHandle MH_getUnsafe;
+    static {
+        // Do these before there is a SM installed.
+        C_Unsafe = sun.misc.Unsafe.class;  // EXPECT A WARNING ON THIS LINE
+        Lookup lookup = lookup();
+        MethodHandle gumh = null;
+        try {
+            gumh = lookup.findStatic(C_Unsafe, "getUnsafe", methodType(C_Unsafe));
+        } catch (ReflectiveOperationException ex) {
+            throw new InternalError(ex.toString());
+        }
+        MH_getUnsafe = gumh;
+        // Try some different lookups:
+        try {
+            lookup.in(Object.class).findStatic(C_Unsafe, "getUnsafe", methodType(C_Unsafe));
+        } catch (ReflectiveOperationException ex) {
+            throw new InternalError(ex.toString());
+        }
+        lookup = lookup().in(C_Unsafe);
+        try {
+            lookup.in(C_Unsafe).findStatic(C_Unsafe, "getUnsafe", methodType(C_Unsafe));
+        } catch (ReflectiveOperationException ex) {
+            throw new InternalError(ex.toString());
+        }
+    }
+
+    public static void main(String[] args) throws Throwable {
+        System.setSecurityManager(new SecurityManager());
+        Lookup lookup = lookup();
+        testBasic(lookup);
+        testDoPriv(lookup);
+        testSetVar();
+        Lookup l2 = lookup.in(Object.class);
+        System.out.println("=== "+l2);
+        testBasic(l2);
+        testDoPriv(l2);
+        Lookup l3 = lookup.in(C_Unsafe);
+        System.out.println("=== "+l3);
+        testBasic(l3);
+        testDoPriv(l3);
+        if (failure != null)
+            throw failure;
+    }
+
+    private static Throwable failure;
+    private static void fail(Throwable ex) {
+        if (failure == null)
+            failure = ex;
+        StackTraceElement frame = new Exception().getStackTrace()[1];
+        System.out.printf("Failed at %s:%d: %s\n", frame.getFileName(), frame.getLineNumber(), ex);
+    }
+    private static void ok(Throwable ex) {
+        StackTraceElement frame = new Exception().getStackTrace()[1];
+        System.out.printf("OK at %s:%d: %s\n", frame.getFileName(), frame.getLineNumber(), ex);
+    }
+
+    private static void testBasic(Lookup lookup) throws Throwable {
+        // Verify that we can't get to this guy under the SM:
+        try {
+            MethodHandle badmh = lookup.findStatic(C_Unsafe, "getUnsafe", methodType(C_Unsafe));
+            assert(badmh.type() == methodType(C_Unsafe));
+            badmh = badmh.asType(badmh.type().generic());
+            Object u = C_Unsafe.cast(badmh.invokeExact());
+            assert(C_Unsafe.isInstance(u));
+            fail(new AssertionError("got mh to getUnsafe!"));
+        } catch (SecurityException ex) {
+            ok(ex);
+        }
+        try {
+            Object u = MH_getUnsafe.invokeWithArguments();
+            assert(C_Unsafe.isInstance(u));
+            fail(new AssertionError("got the Unsafe object! (MH invoke)"));
+        } catch (SecurityException ex) {
+            ok(ex);
+        }
+        try {
+            MethodHandle mh = MH_getUnsafe;
+            mh = mh.asType(mh.type().generic());
+            mh = foldArguments(identity(Object.class), mh);
+            mh = filterReturnValue(mh, identity(Object.class));
+            Object u = mh.invokeExact();
+            assert(C_Unsafe.isInstance(u));
+            fail(new AssertionError("got the Unsafe object! (MH invokeWithArguments)"));
+        } catch (SecurityException ex) {
+            ok(ex);
+        }
+    }
+
+    private static void testDoPriv(Lookup lookup) throws Throwable {
+        PrivilegedAction privAct = MethodHandleProxies.asInterfaceInstance(PrivilegedAction.class, MH_getUnsafe);
+        try {
+            Object u = AccessController.doPrivileged(privAct);
+            assert(C_Unsafe.isInstance(u));
+            fail(new AssertionError("got the Unsafe object! (static doPriv)"));
+        } catch (SecurityException ex) {
+            ok(ex);
+        }
+        MethodHandle MH_doPriv = lookup.findStatic(AccessController.class, "doPrivileged",
+                                                   methodType(Object.class, PrivilegedAction.class));
+        MH_doPriv = MH_doPriv.bindTo(privAct);
+        try {
+            Object u = MH_doPriv.invoke();
+            assert(C_Unsafe.isInstance(u));
+            fail(new AssertionError("got the Unsafe object! (MH + doPriv)"));
+        } catch (SecurityException ex) {
+            ok(ex);
+        }
+        // try one more layer of indirection:
+        Runnable rbl = MethodHandleProxies.asInterfaceInstance(Runnable.class, MH_doPriv);
+        try {
+            rbl.run();
+            fail(new AssertionError("got the Unsafe object! (Runnable + MH + doPriv)"));
+        } catch (SecurityException ex) {
+            ok(ex);
+        }
+    }
+
+    private static void testSetVar() throws Throwable {
+        {
+            // Test the box pattern:
+            Object[] box = new Object[1];
+            MethodHandle MH_getFoo = identity(Object.class).bindTo("foo");
+            MethodHandle MH_storeToBox = insertArguments(arrayElementSetter(Object[].class), 0, box, 0);
+            MethodHandle mh = filterReturnValue(MH_getFoo, MH_storeToBox);
+            mh.invokeExact();
+            assert(box[0] == "foo");
+        }
+        {
+            Object[] box = new Object[1];
+            MethodHandle MH_storeToBox = insertArguments(arrayElementSetter(Object[].class), 0, box, 0);
+            MethodHandle mh = filterReturnValue(MH_getUnsafe.asType(MH_getUnsafe.type().generic()), MH_storeToBox);
+            try {
+                mh.invokeExact();
+                Object u = box[0];
+                assert(C_Unsafe.isInstance(u));
+                fail(new AssertionError("got the Unsafe object! (MH + setElement)"));
+            } catch (SecurityException ex) {
+                ok(ex);
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/lang/invoke/7196190/jtreg.security.policy	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,9 @@
+/*
+ * security policy used by the test process
+ * must allow file reads so that jtreg itself can run
+ */
+
+grant {
+  // standard test activation permissions
+  permission java.io.FilePermission "*", "read";
+};
--- a/test/java/lang/invoke/BigArityTest.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/lang/invoke/BigArityTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -70,7 +70,7 @@
                 MethodHandles.lookup().unreflect(
                     BigArityTest.class.getDeclaredMethod("hashArguments", Object[].class));
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw new Error(ex);
         }
     }
     static MethodHandle MH_hashArguments(int arity) {
--- a/test/java/lang/invoke/PrivateInvokeTest.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/lang/invoke/PrivateInvokeTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -145,21 +145,21 @@
             MH_DEBUG_STRING = DIRECT_INVOKER_LOOKUP
                     .findVirtual(MethodHandle.class, "debugString", methodType(String.class));
         } catch (ReflectiveOperationException ex) {
-            throw new InternalError(ex);
+            throw new Error(ex);
         }
     }
     private Object internalMemberName(MethodHandle mh) {
         try {
             return MH_INTERNAL_MEMBER_NAME.invokeExact(mh);
         } catch (Throwable ex) {
-            throw new InternalError(ex);
+            throw new Error(ex);
         }
     }
     private String debugString(MethodHandle mh) {
         try {
             return (String) MH_DEBUG_STRING.invokeExact(mh);
         } catch (Throwable ex) {
-            throw new InternalError(ex);
+            throw new Error(ex);
         }
     }
     private static MethodHandle directInvoker(int refKind, MethodType mtype) {
--- a/test/java/lang/ref/Basic.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/lang/ref/Basic.java	Mon Nov 05 10:33:18 2012 -0500
@@ -105,6 +105,7 @@
             System.err.println("GC " + i);
             Thread.sleep(10);
             System.gc();
+            System.runFinalization();
 
             showReferences();
             while ((r = q2.poll()) != null) {
--- a/test/java/net/URL/Test.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/net/URL/Test.java	Mon Nov 05 10:33:18 2012 -0500
@@ -322,10 +322,6 @@
         test("ftp://ftp.is.co.za/rfc/rfc1808.txt")
             .s("ftp").h("ftp.is.co.za").p("/rfc/rfc1808.txt").z();
 
-        test("gopher://spinaltap.micro.umn.edu/00/Weather/California/Los%20Angeles")
-            .s("gopher").h("spinaltap.micro.umn.edu")
-            .p("/00/Weather/California/Los%20Angeles").z();
-
         test("http://www.math.uio.no/faq/compression-faq/part1.html")
             .s("http").h("www.math.uio.no").p("/faq/compression-faq/part1.html").z();
 
--- a/test/java/util/PluggableLocale/CurrencyNameProviderTest.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/util/PluggableLocale/CurrencyNameProviderTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -48,10 +48,13 @@
 
     void test1() {
         com.bar.CurrencyNameProviderImpl cnp = new com.bar.CurrencyNameProviderImpl();
+        com.bar.CurrencyNameProviderImpl2 cnp2 = new com.bar.CurrencyNameProviderImpl2();
         Locale[] availloc = Locale.getAvailableLocales();
         Locale[] testloc = availloc.clone();
         List<Locale> jreimplloc = Arrays.asList(LocaleProviderAdapter.forJRE().getCurrencyNameProvider().getAvailableLocales());
-        List<Locale> providerloc = Arrays.asList(cnp.getAvailableLocales());
+        List<Locale> providerloc = new ArrayList<Locale>();
+        providerloc.addAll(Arrays.asList(cnp.getAvailableLocales()));
+        providerloc.addAll(Arrays.asList(cnp2.getAvailableLocales()));
 
         for (Locale target: availloc) {
             // pure JRE implementation
@@ -79,8 +82,13 @@
                 String providerscurrency = null;
                 String providersname = null;
                 if (providerloc.contains(target)) {
+                    if (cnp.isSupportedLocale(target)) {
                     providerscurrency = cnp.getSymbol(c.getCurrencyCode(), target);
                     providersname = cnp.getDisplayName(c.getCurrencyCode(), target);
+                    } else {
+                        providerscurrency = cnp2.getSymbol(c.getCurrencyCode(), target);
+                        providersname = cnp2.getDisplayName(c.getCurrencyCode(), target);
+                    }
                 }
 
                 // JRE's name
@@ -109,18 +117,22 @@
     final String pattern = "###,###\u00A4";
     final String YEN_IN_OSAKA = "100,000\u5186\u3084\u3002";
     final String YEN_IN_KYOTO = "100,000\u5186\u3069\u3059\u3002";
+    final String YEN_IN_TOKYO= "100,000JPY-tokyo";
     final Locale OSAKA = new Locale("ja", "JP", "osaka");
     final Locale KYOTO = new Locale("ja", "JP", "kyoto");
+    final Locale TOKYO = new Locale("ja", "JP", "tokyo");
     Integer i = new Integer(100000);
     String formatted;
     DecimalFormat df;
 
     void test2() {
+        Locale defloc = Locale.getDefault();
+
         try {
             df = new DecimalFormat(pattern, DecimalFormatSymbols.getInstance(OSAKA));
             System.out.println(formatted = df.format(i));
             if(!formatted.equals(YEN_IN_OSAKA)) {
-                throw new RuntimeException("formatted zone names mismatch. " +
+                throw new RuntimeException("formatted currency names mismatch. " +
                     "Should match with " + YEN_IN_OSAKA);
             }
 
@@ -130,13 +142,25 @@
             df = new DecimalFormat(pattern, DecimalFormatSymbols.getInstance());
             System.out.println(formatted = df.format(i));
             if(!formatted.equals(YEN_IN_KYOTO)) {
-                throw new RuntimeException("formatted zone names mismatch. " +
+                throw new RuntimeException("formatted currency names mismatch. " +
                     "Should match with " + YEN_IN_KYOTO);
             }
 
             df.parse(YEN_IN_KYOTO);
+
+            Locale.setDefault(TOKYO);
+            df = new DecimalFormat(pattern, DecimalFormatSymbols.getInstance());
+            System.out.println(formatted = df.format(i));
+            if(!formatted.equals(YEN_IN_TOKYO)) {
+                throw new RuntimeException("formatted currency names mismatch. " +
+                    "Should match with " + YEN_IN_TOKYO);
+            }
+
+            df.parse(YEN_IN_TOKYO);
         } catch (ParseException pe) {
             throw new RuntimeException("parse error occured" + pe);
+        } finally {
+            Locale.setDefault(defloc);
         }
     }
 }
--- a/test/java/util/PluggableLocale/CurrencyNameProviderTest.sh	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/util/PluggableLocale/CurrencyNameProviderTest.sh	Mon Nov 05 10:33:18 2012 -0500
@@ -23,6 +23,6 @@
 #!/bin/sh
 #
 # @test
-# @bug 4052440
+# @bug 4052440 8000997
 # @summary CurrencyNameProvider tests
 # @run shell ExecTest.sh bar CurrencyNameProviderTest true
--- a/test/java/util/PluggableLocale/GenericTest.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/util/PluggableLocale/GenericTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -38,6 +38,7 @@
     com.foo.DecimalFormatSymbolsProviderImpl decimalFSP = new com.foo.DecimalFormatSymbolsProviderImpl();
     com.foo.NumberFormatProviderImpl numberFP = new com.foo.NumberFormatProviderImpl();
     com.bar.CurrencyNameProviderImpl currencyNP = new com.bar.CurrencyNameProviderImpl();
+    com.bar.CurrencyNameProviderImpl2 currencyNP2 = new com.bar.CurrencyNameProviderImpl2();
     com.bar.LocaleNameProviderImpl localeNP = new com.bar.LocaleNameProviderImpl();
     com.bar.TimeZoneNameProviderImpl tzNP = new com.bar.TimeZoneNameProviderImpl();
     com.bar.CalendarDataProviderImpl calDataP = new com.bar.CalendarDataProviderImpl();
@@ -68,6 +69,7 @@
         expected.addAll(Arrays.asList(decimalFSP.getAvailableLocales()));
         expected.addAll(Arrays.asList(numberFP.getAvailableLocales()));
         expected.addAll(Arrays.asList(currencyNP.getAvailableLocales()));
+        expected.addAll(Arrays.asList(currencyNP2.getAvailableLocales()));
         expected.addAll(Arrays.asList(localeNP.getAvailableLocales()));
         expected.addAll(Arrays.asList(tzNP.getAvailableLocales()));
         expected.addAll(Arrays.asList(calDataP.getAvailableLocales()));
Binary file test/java/util/PluggableLocale/barprovider.jar has changed
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/util/PluggableLocale/providersrc/CurrencyNameProviderImpl2.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2012, 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.
+ */
+/*
+ *
+ */
+
+package com.bar;
+
+import java.util.*;
+import java.util.spi.*;
+
+import com.foobar.Utils;
+
+public class CurrencyNameProviderImpl2 extends CurrencyNameProvider {
+    static Locale[] avail = {new Locale("ja", "JP", "tokyo")};
+    public Locale[] getAvailableLocales() {
+        return avail;
+    }
+
+    @Override
+    public String getSymbol(String c, Locale locale) {
+        if (!Utils.supportsLocale(Arrays.asList(avail), locale)) {
+            throw new IllegalArgumentException("locale is not supported: "+locale);
+        }
+
+        if (c.equals("JPY") && Utils.supportsLocale(avail[0], locale)) {
+            return "JPY-tokyo";
+        }
+        return null;
+    }
+
+    @Override
+    public String getDisplayName(String c, Locale locale) {
+        if (!Utils.supportsLocale(Arrays.asList(avail), locale)) {
+            throw new IllegalArgumentException("locale is not supported: "+locale);
+        }
+
+        if (c.equals("JPY") && Utils.supportsLocale(avail[0], locale)) {
+            return "JPY-tokyo";
+        }
+        return null;
+    }
+}
--- a/test/java/util/PluggableLocale/providersrc/Makefile	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/util/PluggableLocale/providersrc/Makefile	Mon Nov 05 10:33:18 2012 -0500
@@ -35,6 +35,7 @@
 
 BARFILES_JAVA = \
     CurrencyNameProviderImpl.java \
+    CurrencyNameProviderImpl2.java \
     TimeZoneNameProviderImpl.java \
     LocaleNameProviderImpl.java \
     CalendarDataProviderImpl.java \
--- a/test/java/util/PluggableLocale/providersrc/java.util.spi.CurrencyNameProvider	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/java/util/PluggableLocale/providersrc/java.util.spi.CurrencyNameProvider	Mon Nov 05 10:33:18 2012 -0500
@@ -5,3 +5,4 @@
 # implementation class
 #
 com.bar.CurrencyNameProviderImpl
+com.bar.CurrencyNameProviderImpl2
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/util/logging/MemoryHandlerTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,156 @@
+/*
+ * Copyright (c) 2012, 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 7159567
+ * @summary Test of configuring a MemoryHandler sub-class handler target via logging.properties
+ * @run main/othervm MemoryHandlerTest
+ */
+import java.io.File;
+import java.io.IOException;
+import java.util.logging.Handler;
+import java.util.logging.Level;
+import java.util.logging.LogManager;
+import java.util.logging.LogRecord;
+import java.util.logging.Logger;
+import java.util.logging.MemoryHandler;
+
+public class MemoryHandlerTest {
+
+    static final String CFG_FILE_PROP = "java.util.logging.config.file";
+    static final String LM_PROP_FNAME = "MemoryHandlerTest.props";
+    static Logger logger;
+
+    public static void main(String... args) throws IOException {
+        // load logging.propertes for the test
+        String tstSrc = System.getProperty("test.src", ".");
+        File fname = new File(tstSrc, LM_PROP_FNAME);
+        String prop = fname.getCanonicalPath();
+        System.setProperty(CFG_FILE_PROP, prop);
+        LogManager logMgr = LogManager.getLogManager();
+        // create a logger
+        logger = Logger.getLogger(MemoryHandlerTest.class.getName());
+        // don't have parent handlers get log messages
+        logger.setUseParentHandlers(false);
+        //
+        // Test 1,2: create a CustomMemoryHandler which in the config has
+        // specified a target of CustomTargetHandler.  (1) Make sure that it
+        // is created and (2) that the target handler is loaded.
+        //
+        CustomMemoryHandler cmh = new CustomMemoryHandler();
+        try {
+            logger.addHandler(cmh);
+        } catch (RuntimeException rte) {
+            throw new RuntimeException(
+                "Test Failed: did not load java.util.logging.ConsoleHandler as expected",
+                rte);
+        }
+        // if we get here and our config has been processed properly, then we
+        // should have loaded our target handler
+        if (CustomTargetHandler.numLoaded !=1) {
+            throw new RuntimeException(
+                "Test failed: did not load CustomTargetHandler as expected");
+        }
+        //
+        // Test 3: try to add a handler with no target.  This should fail with
+        // an exception
+        CustomMemoryHandlerNoTarget cmhnt = null;
+        try {
+            cmhnt = new CustomMemoryHandlerNoTarget();
+        } catch (RuntimeException re) {
+            // expected -- no target specified
+            System.out.println("Info: " + re.getMessage() + " as expected.");
+        }
+        if (cmhnt != null) {
+            throw new RuntimeException(
+                "Test Failed: erroneously loaded CustomMemoryHandlerNoTarget");
+        }
+
+        // Test 4: log a message and check that the target handler is actually used
+        logger.log(Level.WARNING, "Unused");
+        if (CustomTargetHandler.numPublished != 1) {
+            throw new RuntimeException("Test failed: CustomTargetHandler was not used");
+        }
+
+        // Test 5: make sure that SimpleTargetHandler hasn't been erroneously called
+        if (SimpleTargetHandler.numPublished != 0) {
+            throw new RuntimeException("Test failed: SimpleTargetHandler has been used");
+        }
+
+        // Test 6: try using SimpleTargetHanlder via standard MemoryHandler
+        // (which has target set to SimpleTargetHandler)
+        MemoryHandler mh = new MemoryHandler();
+        mh.publish(new LogRecord(Level.INFO, "Unused msg to MemoryHandler"));
+        // see if it made it to the SimpleTargetHandler
+        if (SimpleTargetHandler.numPublished != 1) {
+            throw new RuntimeException("Test failed: SimpleTargetHandler was not used");
+        }
+    }
+
+    public static class CustomMemoryHandler extends MemoryHandler {
+    }
+
+    public static class CustomMemoryHandlerNoTarget extends MemoryHandler {
+    }
+
+    public static class CustomTargetHandler extends Handler {
+
+        public static int numPublished;
+        public static int numLoaded;
+
+        public CustomTargetHandler() {
+            numLoaded++;
+        }
+
+        @Override
+        public void publish(LogRecord unused) {
+            numPublished++;
+        }
+
+        @Override
+        public void flush() {
+        }
+
+        @Override
+        public void close() throws SecurityException {
+        }
+    }
+
+    public static class SimpleTargetHandler extends Handler {
+        public static int numPublished;
+
+        @Override
+        public void publish(LogRecord unused) {
+            numPublished++;
+        }
+
+        @Override
+        public void flush() {
+        }
+
+        @Override
+        public void close() throws SecurityException {
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/java/util/logging/MemoryHandlerTest.props	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,9 @@
+.level= INFO
+MemoryHandlerTest$CustomMemoryHandler.push=WARNING
+MemoryHandlerTest$CustomMemoryHandlerNoTarget.push=WARNING
+MemoryHandlerTest$CustomMemoryHandler.target=MemoryHandlerTest$CustomTargetHandler
+handlers=java.util.logging.ConsoleHandler,MemoryHandlerTest$CustomMemoryHandler,MemoryHandlerTest$CustomMemoryHandlerNoTarget
+java.util.logging.ConsoleHandler.formatter = java.util.logging.SimpleFormatter
+java.util.logging.ConsoleHandler.level = INFO
+java.util.logging.MemoryHandler.target=MemoryHandlerTest$SimpleTargetHandler
+java.util.logging.MemoryHandler.push = INFO
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/javax/crypto/sanity/CheckManifestForRelease.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,123 @@
+/*
+ * Copyright (c) 2012, 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 7197071
+ * @summary Makefiles for various security providers aren't including
+ *          the default manifest.
+ */
+import java.net.*;
+import java.io.*;
+
+/**
+ * When the Java specification version is incremented, all of the providers
+ * must be recompiled with the proper implementation version to match.
+ */
+public class CheckManifestForRelease {
+
+    /**
+     * @param args the command line arguments
+     */
+    public static void main(String[] args) throws Exception {
+        checkFileManifests();
+    }
+
+    /*
+     * Iterate over the files of interest: JCE framework and providers
+     */
+    static private void checkFileManifests() throws Exception {
+        System.out.println("=============");
+        String libDirName = System.getProperty("java.home", ".") + "/lib";
+        String extDirName = libDirName + "/ext";
+
+        System.out.println("Checking Manifest in directory: \n    " +
+            extDirName);
+
+        /*
+         * Current list of JCE providers, all of which currently live in
+         * the extensions directory.  Add if more are created.
+         */
+        String[] providers = new String[]{
+            "sunjce_provider.jar",
+            "sunec.jar",
+            "sunmscapi.jar",
+            "sunpkcs11.jar",
+            "ucrypto.jar"
+        };
+
+        checkManifest(libDirName, "jce.jar");
+        for (String provider : providers) {
+            checkManifest(extDirName, provider);
+        }
+        System.out.println("Passed.");
+    }
+
+    // Helper method to format the URL properly.
+    static private String formatURL(String dir, String file) {
+        return "jar:file:///" + dir + "/" + file + "!/";
+    }
+
+    static private String specVersion =
+        System.getProperty("java.specification.version");
+
+    /*
+     * Test the root cause, which is that there were no manifest values
+     * for many of the providers, and for those that had them, there was
+     * no test to make sure that the impl version was appropriate for
+     * the spec version.
+     */
+    static private void checkManifest(String dir, String file)
+            throws Exception {
+
+        System.out.println("Checking: " + file);
+
+        String url = formatURL(dir, file);
+        JarURLConnection urlc =
+            (JarURLConnection) (new URL(url).openConnection());
+
+        String implVersion;
+        try {
+            implVersion = urlc.getManifest().getMainAttributes().getValue(
+                "Implementation-Version");
+        } catch (FileNotFoundException e) {
+            /*
+             * If the file doesn't exist (e.g. mscapi on solaris),
+             * skip it. If there are other problems, fail out.
+             */
+            System.out.println("    " + file + " not found, skipping...");
+            return;
+        }
+
+        if (implVersion == null) {
+            throw new Exception(
+                "Implementation-Version not found in Manifest");
+        }
+
+        if (!implVersion.startsWith(specVersion)) {
+            throw new Exception(
+                "Implementation-Version does not match " +
+                "Specification-Version");
+        }
+    }
+}
--- a/test/javax/management/remote/mandatory/URLTest.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/javax/management/remote/mandatory/URLTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -24,8 +24,6 @@
 /*
  * @test
  * @bug 5057532
- * @ignore Test will fail until 6338951 is resolved (java.net.URI now
- * accepts "http://-a").
  * @summary Tests that host names are parsed correctly in URLs
  * @author Eamonn McManus
  * @run clean URLTest
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/javax/swing/JMenuItem/4654927/bug4654927.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,152 @@
+/*
+ * Copyright (c) 2012, 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 4654927
+ * @summary Clicking on Greyed Menuitems closes the Menubar Dropdown
+ * @author Alexander Potochkin
+ * @library ../../regtesthelpers
+ * @build Util
+ * @run main bug4654927
+ */
+
+import javax.swing.*;
+
+import java.awt.*;
+import java.awt.event.InputEvent;
+import java.util.concurrent.Callable;
+import sun.awt.SunToolkit;
+
+public class bug4654927 {
+
+    private static volatile JMenu menu;
+    private static volatile JMenuItem menuItem;
+
+    public static void main(String[] args) throws Exception {
+        String systemLAF = UIManager.getSystemLookAndFeelClassName();
+        // the test is not applicable to Motif L&F
+        if(systemLAF.endsWith("MotifLookAndFeel")){
+            return;
+        }
+
+        UIManager.setLookAndFeel(systemLAF);
+        SunToolkit toolkit = (SunToolkit) Toolkit.getDefaultToolkit();
+        Robot robot = new Robot();
+        robot.setAutoDelay(10);
+
+        SwingUtilities.invokeAndWait(new Runnable() {
+
+            public void run() {
+                createAndShowUI();
+            }
+        });
+        toolkit.realSync();
+
+        // test mouse press
+        Point point = Util.getCenterPoint(menu);
+        robot.mouseMove(point.x, point.y);
+        robot.mousePress(InputEvent.BUTTON1_MASK);
+        robot.mouseRelease(InputEvent.BUTTON1_MASK);
+        toolkit.realSync();
+
+        point = Util.getCenterPoint(menuItem);
+        robot.mouseMove(point.x, point.y);
+        robot.mousePress(InputEvent.BUTTON1_MASK);
+        robot.mouseRelease(InputEvent.BUTTON1_MASK);
+        toolkit.realSync();
+
+        if (!isMenuItemShowing()) {
+            throw new RuntimeException("Popup is unexpectedly closed");
+        }
+
+        // test mouse drag
+        point = Util.getCenterPoint(menu);
+        robot.mouseMove(point.x, point.y);
+        Point menuLocation = Util.invokeOnEDT(new Callable<Point>() {
+
+            @Override
+            public Point call() throws Exception {
+                return menu.getLocationOnScreen();
+            }
+        });
+
+        Point itemLocation = Util.invokeOnEDT(new Callable<Point>() {
+
+            @Override
+            public Point call() throws Exception {
+                return menuItem.getLocationOnScreen();
+            }
+        });
+
+        int x0 = menuLocation.x + 10;
+        int y0 = menuLocation.y + 10;
+        int x1 = itemLocation.x + 10;
+        int y1 = itemLocation.y + 10;
+
+        // close menu
+        robot.mousePress(InputEvent.BUTTON1_MASK);
+        robot.mouseRelease(InputEvent.BUTTON1_MASK);
+        toolkit.realSync();
+
+        robot.mousePress(InputEvent.BUTTON1_MASK);
+        Util.glide(robot, x0, y0, x1, y1);
+        robot.mouseRelease(InputEvent.BUTTON1_MASK);
+        toolkit.realSync();
+
+        if (!isMenuItemShowing()) {
+            throw new RuntimeException("Popup is unexpectedly closed");
+        }
+    }
+
+    private static boolean isMenuItemShowing() throws Exception {
+        return Util.invokeOnEDT(new Callable<Boolean>() {
+
+            @Override
+            public Boolean call() throws Exception {
+                return menuItem.isShowing();
+            }
+        });
+    }
+
+    private static void createAndShowUI() {
+        JFrame frame = new JFrame();
+        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
+
+        menu = new JMenu("Menu");
+        menu.add(new JMenuItem("menuItem"));
+        menuItem = new JMenuItem("menuItem");
+        menuItem.setEnabled(false);
+        menu.add(menuItem);
+        menu.add(new JMenuItem("menuItem"));
+
+        JMenuBar bar = new JMenuBar();
+        bar.add(menu);
+        frame.setJMenuBar(bar);
+
+        frame.setSize(200, 200);
+        frame.setLocationRelativeTo(null);
+        frame.setVisible(true);
+
+    }
+}
--- a/test/javax/swing/regtesthelpers/Util.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/javax/swing/regtesthelpers/Util.java	Mon Nov 05 10:33:18 2012 -0500
@@ -157,6 +157,36 @@
     }
 
     /**
+     * Moves mouse smoothly from (x0, y0) to (x1, y1).
+     */
+    public static void glide(Robot robot, int x0, int y0, int x1, int y1) throws AWTException {
+        float dmax = (float) Math.max(Math.abs(x1 - x0), Math.abs(y1 - y0));
+        float dx = (x1 - x0) / dmax;
+        float dy = (y1 - y0) / dmax;
+
+        for (int i = 0; i <= dmax; i += 10) {
+            robot.mouseMove((int) (x0 + dx * i), (int) (y0 + dy * i));
+        }
+    }
+
+    /**
+     * Gets component center point
+     *
+     * @return center point of the <code>component</code>
+     */
+    public static Point getCenterPoint(final Component component) throws Exception {
+        return Util.invokeOnEDT(new Callable<Point>() {
+
+            @Override
+            public Point call() throws Exception {
+                Point p = component.getLocationOnScreen();
+                Dimension size = component.getSize();
+                return new Point(p.x + size.width / 2, p.y + size.height / 2);
+            }
+        });
+    }
+
+    /**
      * Invokes the <code>task</code> on the EDT thread.
      *
      * @return result of the <code>task</code>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/jdk/asm/AsmSanity.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2012, 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 7197401
+ * @summary Add a subset of the org.objectweb.asm packages to jdk8
+ * This test doesn't test asm functionality, it just tests the presence of
+ * asm in the jdk.
+ * These compile/run commands do the following:
+ * - Verify that asm is not in ct.sym so user code that refs it won't compile.
+ * - Verify that asm really is in rt.jar and can be accessed when ct.sym is not used.
+ * - Verify that if user code is compiled without ct.sym, it can't access asm classes
+ *   at runtime when a security manager is in use.
+ *
+ * @compile/fail AsmSanity.java
+ *
+ * @compile -XDignore.symbol.file=true AsmSanity.java
+ * @run main/othervm AsmSanity
+ *
+ * @run main/othervm/fail AsmSanity secure
+ *
+ */
+
+
+// Verify that the expected asm pkgs are present
+import jdk.internal.org.objectweb.asm.*;
+import jdk.internal.org.objectweb.asm.commons.*;
+import jdk.internal.org.objectweb.asm.signature.*;
+import jdk.internal.org.objectweb.asm.tree.*;
+import jdk.internal.org.objectweb.asm.tree.analysis.*;
+import jdk.internal.org.objectweb.asm.util.*;
+
+// Verify that we can actually run some of the asm code.
+public class AsmSanity {
+
+    static public void main(String[] args) {
+        if (args.length == 0) {
+            System.out.println("-- Running without SecurityManager");
+            new Label();
+            System.out.println("-- Passed");
+            return;
+        }
+
+        if (args[0].equals("secure")) {
+            System.out.println("-- Running with SecurityManager");
+            java.lang.SecurityManager sm = new SecurityManager();
+            System.setSecurityManager(sm);
+            // This should cause an accessClassInPackage exception
+            new Label();
+            return;
+        }
+        throw new Error("-- Failed:  Unknown argument to main: " + args[0]);
+    }
+}
--- a/test/sun/security/krb5/ConfPlusProp.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/krb5/ConfPlusProp.java	Mon Nov 05 10:33:18 2012 -0500
@@ -25,6 +25,7 @@
  * @bug 6857795
  * @bug 6858589
  * @bug 6972005
+ * @compile -XDignore.symbol.file ConfPlusProp.java
  * @run main/othervm ConfPlusProp
  * @summary krb5.conf ignored if system properties on realm and kdc are provided
  */
@@ -75,7 +76,7 @@
         check("R1", "k1");
         check("R2", "old");
         check("R3", null);
-        if (!config.getDefault("forwardable", "libdefaults").equals("well")) {
+        if (!config.get("libdefaults", "forwardable").equals("well")) {
             throw new Exception("Extra config error");
         }
 
@@ -103,7 +104,7 @@
             check("R1", null);
             check("R2", null);
             check("R3", null);
-            if (config.getDefault("forwardable", "libdefaults") != null) {
+            if (config.get("libdefaults", "forwardable") != null) {
                 throw new Exception("Extra config error");
             }
         }
@@ -121,7 +122,7 @@
         check("R1", "k1");
         check("R2", "k2");
         check("R3", "k2");
-        if (!config.getDefault("forwardable", "libdefaults").equals("well")) {
+        if (!config.get("libdefaults", "forwardable").equals("well")) {
             throw new Exception("Extra config error");
         }
 
@@ -143,7 +144,7 @@
         check("R1", "k2");
         check("R2", "k2");
         check("R3", "k2");
-        if (config.getDefault("forwardable", "libdefaults") != null) {
+        if (config.get("libdefaults", "forwardable") != null) {
             throw new Exception("Extra config error");
         }
     }
--- a/test/sun/security/krb5/DnsFallback.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/krb5/DnsFallback.java	Mon Nov 05 10:33:18 2012 -0500
@@ -28,12 +28,20 @@
  * @summary fix dns_fallback parse error, and use dns by default
  */
 
-import sun.security.krb5.*;
 import java.io.*;
+import java.lang.reflect.Method;
+import sun.security.krb5.Config;
 
 public class DnsFallback {
+
+    static Method useDNS_Realm;
+
     public static void main(String[] args) throws Exception {
 
+        useDNS_Realm = Config.class.getDeclaredMethod("useDNS_Realm");
+        useDNS_Realm.setAccessible(true);
+
+
         // for 6673164
         check("true", "true", true);
         check("false", "true", false);
@@ -48,22 +56,25 @@
         check(null, null, true);
     }
 
-    static void check(String realm, String fallback, boolean output) throws Exception {
-        FileOutputStream fo = new FileOutputStream("dnsfallback.conf");
-        StringBuffer sb = new StringBuffer();
-        sb.append("[libdefaults]\n");
-        if (realm != null) {
-            sb.append("dns_lookup_realm=" + realm + "\n");
+    static void check(String realm, String fallback, boolean output)
+            throws Exception {
+
+        try (PrintStream ps =
+                new PrintStream(new FileOutputStream("dnsfallback.conf"))) {
+            ps.println("[libdefaults]\n");
+            if (realm != null) {
+                ps.println("dns_lookup_realm=" + realm);
+            }
+            if (fallback != null) {
+                ps.println("dns_fallback=" + fallback);
+            }
         }
-        if (fallback != null) {
-            sb.append("dns_fallback=" + fallback + "\n");
-        }
-        fo.write(sb.toString().getBytes());
-        fo.close();
+
         System.setProperty("java.security.krb5.conf", "dnsfallback.conf");
         Config.refresh();
         System.out.println("Testing " + realm + ", " + fallback + ", " + output);
-        if (Config.getInstance().useDNS_Realm() != output) {
+
+        if (!useDNS_Realm.invoke(Config.getInstance()).equals(output)) {
             throw new Exception("Fail");
         }
     }
--- a/test/sun/security/krb5/ParseConfig.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/krb5/ParseConfig.java	Mon Nov 05 10:33:18 2012 -0500
@@ -23,6 +23,7 @@
 /*
  * @test
  * @bug 6319046
+ * @compile -XDignore.symbol.file ParseConfig.java
  * @run main/othervm ParseConfig
  * @summary Problem with parsing krb5.conf
  */
@@ -37,7 +38,7 @@
 
         String sample = "kdc.example.com kdc2.example.com";
         for ( int i = 0; i < 4; i++ ) {
-            String expected = config.getDefault("kdc", "EXAMPLE_" + i + ".COM");
+            String expected = config.getAll("realms", "EXAMPLE_" + i + ".COM", "kdc");
             if (!sample.equals(expected)) {
                 throw new Exception("krb5.conf: unexpected kdc value \"" +
                         expected + "\"");
--- a/test/sun/security/krb5/auto/BasicKrb5Test.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/krb5/auto/BasicKrb5Test.java	Mon Nov 05 10:33:18 2012 -0500
@@ -25,6 +25,7 @@
  * @test
  * @bug 6706974
  * @summary Add krb5 test infrastructure
+ * @compile -XDignore.symbol.file BasicKrb5Test.java
  * @run main/othervm BasicKrb5Test
  * @run main/othervm BasicKrb5Test des-cbc-crc
  * @run main/othervm BasicKrb5Test des-cbc-md5
@@ -86,7 +87,7 @@
         new OneKDC(etype).writeJAASConf();
 
         System.out.println("Testing etype " + etype);
-        if (etype != null && !EType.isSupported(Config.getInstance().getType(etype))) {
+        if (etype != null && !EType.isSupported(Config.getType(etype))) {
             // aes256 is not enabled on all systems
             System.out.println("Not supported.");
             return;
--- a/test/sun/security/krb5/auto/MaxRetries.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/krb5/auto/MaxRetries.java	Mon Nov 05 10:33:18 2012 -0500
@@ -108,7 +108,7 @@
             if (line.startsWith(">>> KDCCommunication")) {
                 System.out.println(line);
                 if (line.indexOf(timeoutTag) < 0) {
-                    throw new Exception("Wrong timeout value");
+                    throw new Exception("Wrong timeout value" + timeoutTag);
                 }
                 count--;
             }
--- a/test/sun/security/krb5/ccache/EmptyCC.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/krb5/ccache/EmptyCC.java	Mon Nov 05 10:33:18 2012 -0500
@@ -24,9 +24,11 @@
 /*
  * @test
  * @bug 7158329
+ * @bug 8001208
  * @summary NPE in sun.security.krb5.Credentials.acquireDefaultCreds()
  * @compile -XDignore.symbol.file EmptyCC.java
- * @run main EmptyCC
+ * @run main EmptyCC tmpcc
+ * @run main EmptyCC FILE:tmpcc
  */
 import java.io.File;
 import java.io.InputStream;
@@ -40,9 +42,9 @@
 public class EmptyCC {
     public static void main(String[] args) throws Exception {
         final PrincipalName pn = new PrincipalName("dummy@FOO.COM");
-        final String ccache = "tmpcc";
+        final String ccache = args[0];
 
-        if (args.length == 0) {
+        if (args.length == 1) {
             // Main process, write the ccache and launch sub process
             CredentialsCache cache = CredentialsCache.create(pn, ccache);
             cache.save();
@@ -54,6 +56,7 @@
                     "-cp",
                     System.getProperty("test.classes"),
                     "EmptyCC",
+                    ccache,
                     "readcc"
                     );
 
@@ -77,6 +80,14 @@
             if (!cc.equals(ccache)) {
                 throw new Exception("env not set correctly");
             }
+            // 8001208: Fix for KRB5CCNAME not complete
+            // Make sure the ccache is created with bare file name
+            if (CredentialsCache.getInstance() == null) {
+                throw new Exception("Cache not instantiated");
+            }
+            if (!new File("tmpcc").exists()) {
+                throw new Exception("File not found");
+            }
             Credentials.acquireTGTFromCache(pn, null);
         }
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/sun/security/krb5/config/Duplicates.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,72 @@
+/*
+ * Copyright (c) 2012, 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 7184246
+ * @compile -XDignore.symbol.file Duplicates.java
+ * @run main/othervm Duplicates
+ * @summary Simplify Config.get() of krb5
+ */
+
+import sun.security.krb5.Config;
+
+public class Duplicates {
+    public static void main(String[] args) throws Exception {
+        System.setProperty("java.security.krb5.conf",
+                System.getProperty("test.src", ".") +"/k1.conf");
+        Config config = Config.getInstance();
+        config.listTable();
+        String s;
+
+        // Latter overwrites former for root section
+        s = config.get("libdefaults", "default_realm");
+        if (s != null) {
+            throw new Exception();
+        }
+        // Latter overwrites former for strings
+        s = config.get("libdefaults", "default_tkt_enctypes");
+        if (!s.equals("aes256-cts")) {
+            throw new Exception();
+        }
+        // Latter overwrites former for sub-section
+        s = config.get("realms", "R1", "kdc");
+        if (!s.equals("k2")) {
+            throw new Exception(s);
+        }
+        // Duplicate keys in [realms] are merged
+        s = config.getAll("realms", "R2", "kdc");
+        if (!s.equals("k1 k2 k3 k4")) {
+            throw new Exception(s);
+        }
+        // Duplicate keys in [capaths] are merged
+        s = config.getAll("capaths", "R1", "R2");
+        if (!s.equals("R3 R4 R5 R6")) {
+            throw new Exception(s);
+        }
+        // We can be very deep now
+        s = config.get("new", "x", "y", "z", "a", "b", "c");
+        if (!s.equals("d")) {
+            throw new Exception(s);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/sun/security/krb5/config/KdcDefaultOptions.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,46 @@
+/*
+ * Copyright (c) 2012, 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 7195426
+ * @summary kdc_default_options not supported correctly
+ * @compile -XDignore.symbol.file KdcDefaultOptions.java
+ * @run main/othervm KdcDefaultOptions
+ */
+
+import sun.security.krb5.Config;
+import sun.security.krb5.internal.KDCOptions;
+
+public class KdcDefaultOptions {
+    public static void main(String[] args) throws Exception {
+        System.setProperty("java.security.krb5.conf",
+                System.getProperty("test.src", ".") + "/kdc_default_options.conf");
+        Config.refresh();
+        KDCOptions options = new KDCOptions();
+        if (!options.get(KDCOptions.FORWARDABLE) ||
+                !options.get(KDCOptions.PROXIABLE) ||
+                !options.get(KDCOptions.RENEWABLE_OK)) {
+            throw new Exception(options.toString());
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/sun/security/krb5/config/SCDynamicConfigTest.java	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,102 @@
+/*
+ * Copyright (c) 2012, 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 7184246
+ * @summary Simplify Config.get() of krb5
+ */
+import java.lang.reflect.Field;
+import java.lang.reflect.Method;
+import java.util.Hashtable;
+import java.util.Vector;
+import sun.security.krb5.Config;
+import sun.security.krb5.SCDynamicStoreConfig;
+
+public class SCDynamicConfigTest {
+
+    static Vector<Hashtable<String,String>>hosts() {
+        Vector <Hashtable<String,String>> result = new Vector<>();
+        Hashtable<String,String> pair = new Hashtable<>();
+        pair.put("host", "127.0.0.1");
+        result.add(pair);
+        pair = new Hashtable<>();
+        pair.put("host", "127.0.0.2");
+        result.add(pair);
+        return result;
+    }
+
+    public static void main(String[] args) throws Exception {
+        // Reconstruct a typical SCDynamicConfig.getKerberosConfig() output
+        Hashtable<String, Object> conf = new Hashtable<>();
+
+        Hashtable<String, Object> libdefaults = new Hashtable<>();
+        libdefaults.put("default_realm", "REALM.COM");
+        conf.put("libdefaults", libdefaults);
+
+        Hashtable<String, Object> realms = new Hashtable<>();
+        Hashtable<String, Object> thisRealm = new Hashtable<>();
+        realms.put("REALM.COM", thisRealm);
+        thisRealm.put("kpasswd", hosts());
+        thisRealm.put("kadmin", hosts());
+        thisRealm.put("kdc", hosts());
+        conf.put("realms", realms);
+
+        Hashtable<String, Object> domain_realm = new Hashtable<>();
+        domain_realm.put(".realm.com", "REALM.COM");
+        domain_realm.put("realm.com", "REALM.COM");
+        conf.put("domain_realm", domain_realm);
+
+        System.out.println("SCDynamicConfig:\n");
+        System.out.println(conf);
+
+        // Simulate SCDynamicConfig.getConfig() output
+        Method m = SCDynamicStoreConfig.class.getDeclaredMethod(
+                "convertNativeConfig", Hashtable.class);
+        m.setAccessible(true);
+        conf = (Hashtable)m.invoke(null, conf);
+
+        System.out.println("\nkrb5.conf:\n");
+        System.out.println(conf);
+
+        // Feed it into a Config object
+        System.setProperty("java.security.krb5.conf", "not-a-file");
+        Config cf = Config.getInstance();
+        Field f = Config.class.getDeclaredField("stanzaTable");
+        f.setAccessible(true);
+        f.set(cf, conf);
+
+        System.out.println("\nConfig:\n");
+        System.out.println(cf);
+
+        if (!cf.getDefaultRealm().equals("REALM.COM")) {
+            throw new Exception();
+        }
+        if (!cf.getKDCList("REALM.COM").equals("127.0.0.1 127.0.0.2")) {
+            throw new Exception();
+        }
+        if (!cf.get("domain_realm", ".realm.com").equals("REALM.COM")) {
+            throw new Exception();
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/sun/security/krb5/config/k1.conf	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,40 @@
+[libdefaults]
+default_realm = R1
+
+[libdefaults]
+default_tkt_enctypes = aes128-cts
+default_tkt_enctypes = aes256-cts
+
+[realms]
+R1 = {
+    kdc = k1
+}
+R1 = {
+    kdc = k2
+}
+R2 = {
+    kdc = k1
+    kdc = k2 k3
+    admin_server = a1
+    kdc = k4
+}
+
+[capaths]
+R1 = {
+    R2 = R3
+    R2 = R4 R5
+    R2 = R6
+}
+
+[new]
+x = {
+    y = {
+        z = {
+            a = {
+                b = {
+                    c = d
+                }
+            }
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/sun/security/krb5/config/kdc_default_options.conf	Mon Nov 05 10:33:18 2012 -0500
@@ -0,0 +1,3 @@
+[libdefaults]
+default_realm = EXAMPLE.COM
+kdc_default_options = 0x50000010
--- a/test/sun/security/ssl/javax/net/ssl/ServerName/SSLSocketSNISensitive.java	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/security/ssl/javax/net/ssl/ServerName/SSLSocketSNISensitive.java	Mon Nov 05 10:33:18 2012 -0500
@@ -267,6 +267,9 @@
 
         SSLSocket sslSocket = (SSLSocket)sslServerSocket.accept();
         try {
+            sslSocket.setSoTimeout(5000);
+            sslSocket.setSoLinger(true, 5);
+
             InputStream sslIS = sslSocket.getInputStream();
             OutputStream sslOS = sslSocket.getOutputStream();
 
@@ -312,6 +315,9 @@
         sslSocket.setSSLParameters(params);
 
         try {
+            sslSocket.setSoTimeout(5000);
+            sslSocket.setSoLinger(true, 5);
+
             InputStream sslIS = sslSocket.getInputStream();
             OutputStream sslOS = sslSocket.getOutputStream();
 
@@ -519,7 +525,7 @@
                          *
                          * Release the client, if not active already...
                          */
-                        System.err.println("Server died...");
+                        System.err.println("Server died, because of " + e);
                         serverReady = true;
                         serverException = e;
                     }
@@ -547,7 +553,7 @@
                         /*
                          * Our client thread just died.
                          */
-                        System.err.println("Client died...");
+                        System.err.println("Client died, because of " + e);
                         clientException = e;
                     }
                 }
--- a/test/sun/tools/jcmd/jcmd_Output1.awk	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/tools/jcmd/jcmd_Output1.awk	Mon Nov 05 10:33:18 2012 -0500
@@ -16,7 +16,7 @@
 }
 
 # or match on the condition that the class name is not available
-/^[0-9]+ -- process information unavailable$/	{
+/^[0-9]+ -- .*$/	{
 	    current=1;
 	}
 
--- a/test/sun/tools/jps/jps-l_Output1.awk	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/tools/jps/jps-l_Output1.awk	Mon Nov 05 10:33:18 2012 -0500
@@ -16,7 +16,7 @@
 }
 
 # or match on the condition that the class name is not available
-/^[0-9]+ -- process information unavailable$/	{
+/^[0-9]+ -- .*$/	{
 	    matched++;
 	}
 
--- a/test/sun/tools/jps/jps_Output1.awk	Mon Nov 05 10:30:49 2012 -0500
+++ b/test/sun/tools/jps/jps_Output1.awk	Mon Nov 05 10:33:18 2012 -0500
@@ -16,7 +16,7 @@
 }
 
 # or match on the condition that the class name is not available
-/^[0-9]+ -- process information unavailable$/	{
+/^[0-9]+ -- .*$/	{
 	    matched++;
 	}