1 #!/bin/sh
   2 
   3 #
   4 # Copyright (c) 2006, 2014 Oracle and/or its affiliates. All rights reserved.
   5 # DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   6 #
   7 # This code is free software; you can redistribute it and/or modify it
   8 # under the terms of the GNU General Public License version 2 only, as
   9 # published by the Free Software Foundation.
  10 #
  11 # This code is distributed in the hope that it will be useful, but WITHOUT
  12 # ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13 # FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14 # version 2 for more details (a copy is included in the LICENSE file that
  15 # accompanied this code).
  16 #
  17 # You should have received a copy of the GNU General Public License version
  18 # 2 along with this work; if not, write to the Free Software Foundation,
  19 # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20 #
  21 # Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22 # or visit www.oracle.com if you need additional information or have any
  23 # questions.
  24 #
  25 
  26 # @test
  27 # @bug 6270982
  28 # @summary Redefine a class so that the order of external classes in
  29 # the constant pool are changed.
  30 # @author dcubed
  31 #
  32 # @run shell RedefineChangeClassOrder.sh
  33 
  34 compileOptions=-g
  35 
  36 # Would like to run this test with this option:
  37 # -XX:-FailOverToOldVerifier
  38 
  39 # Uncomment this to see the JDI trace
  40 #jdbOptions=-dbgtrace
  41 
  42 createJavaFile()
  43 {
  44     cat <<EOF > $1.java.1
  45 
  46 import java.lang.annotation.Retention;
  47 import java.lang.annotation.RetentionPolicy;
  48 
  49 public class $1 {
  50     public static void main(String[] args) {
  51         new $1().hi(false);
  52         new $1().hi(true);  // @1 breakpoint
  53     }
  54 
  55     public void hi(boolean expected) {
  56         boolean isNewVersion = false; // @1 commentout
  57         // @1 uncomment boolean isNewVersion = true;
  58 
  59         if (expected == isNewVersion) {
  60             System.out.println("PASS: expected and isNewVersion match.");
  61         } else {
  62             System.out.println("FAIL: expected and isNewVersion do not match.");
  63             System.out.println("expected=" + expected
  64               + "  isNewVersion=" + isNewVersion);
  65         }
  66 
  67         Foo1 foo1 = new Foo1();  // @1 commentout
  68         foo1.hi();  // @1 commentout
  69 
  70         // This Hack code block exists to force some verification_type_info
  71         // objects of subtype Object_variable_info into the StackMapTable.
  72         //
  73         // In the redefined code, the above Foo1 code is effectively
  74         // moved after the Foo2 code below which causes things to be
  75         // layed out in a different order in the constant pool. The
  76         // cpool_index in the Object_variable_info has to be updated
  77         // in the redefined code's StackMapTable to refer to right
  78         /// constant pool index in the merged constant pool.
  79         Hack hack = getClass().getAnnotation(Hack.class);
  80         if (hack != null) {
  81             String class_annotation = hack.value();
  82             System.out.println("class annotation is: " + class_annotation);
  83             if (isNewVersion) {
  84                 if (class_annotation.equals("JUNK")) {
  85                     System.out.println("class_annotation is JUNK.");
  86                 } else {
  87                     System.out.println("class_annotation is NOT JUNK.");
  88                 }
  89             }
  90         }
  91 
  92         Foo2 foo2 = new Foo2();
  93         foo2.hi();
  94 
  95         // @1 uncomment Foo1 foo1 = new Foo1();
  96         // @1 uncomment foo1.hi();
  97     }
  98 }
  99 
 100 class Foo1 {
 101     public void hi() {
 102         System.out.println("Hello from " + getClass());
 103     }
 104 }
 105 
 106 class Foo2 {
 107     public void hi() {
 108         System.out.println("Hello from " + getClass());
 109     }
 110 }
 111 
 112 @Retention(RetentionPolicy.RUNTIME)
 113 @interface Hack {
 114     String value();
 115 }
 116 
 117 EOF
 118 }
 119 
 120 # This is called to feed cmds to jdb.
 121 dojdbCmds()
 122 {
 123     setBkpts @1
 124     runToBkpt @1
 125     redefineClass @1
 126     cmd allowExit cont
 127 }
 128 
 129 
 130 mysetup()
 131 {
 132     if [ -z "$TESTSRC" ] ; then
 133         TESTSRC=.
 134     fi
 135 
 136     for ii in . $TESTSRC $TESTSRC/.. ; do
 137         if [ -r "$ii/ShellScaffold.sh" ] ; then
 138             . $ii/ShellScaffold.sh
 139             break
 140         fi
 141     done
 142 }
 143 
 144 # You could replace this next line with the contents
 145 # of ShellScaffold.sh and this script will run just the same.
 146 mysetup
 147 
 148 runit
 149 
 150 debuggeeFailIfPresent 'FAIL:'
 151 pass