diff options
author | Ivan Dubrov <idubrov@guidewire.com> | 2014-04-25 14:15:01 -0700 |
---|---|---|
committer | Ivan Dubrov <idubrov@guidewire.com> | 2014-04-25 14:16:33 -0700 |
commit | 597ce0d6ae31ce14a5cb635e907f8428250ab58b (patch) | |
tree | 56716c4c34250bed0d32320148ec9ca20e5da884 /dcevm | |
parent | af98d8dd7024b07a21169932f486d15596edf613 (diff) | |
download | dcevm-597ce0d6ae31ce14a5cb635e907f8428250ab58b.tar.gz dcevm-597ce0d6ae31ce14a5cb635e907f8428250ab58b.zip |
Adding 'full' tests
* Killing test suites (you can run tests by package)
* Introduced categories to run certain tests only on 'light'/'full'
Diffstat (limited to 'dcevm')
35 files changed, 2652 insertions, 449 deletions
diff --git a/dcevm/src/test/java7/com/github/dcevm/test/eval/EvalTestSuite.java b/dcevm/src/main/java/com/github/dcevm/FieldRedefinitionPolicy.java index f162c523..cf3733c9 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/eval/EvalTestSuite.java +++ b/dcevm/src/main/java/com/github/dcevm/FieldRedefinitionPolicy.java @@ -21,22 +21,17 @@ * questions. * */ +package com.github.dcevm; -package com.github.dcevm.test.eval; - -import org.junit.runner.RunWith; -import org.junit.runners.Suite; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; /** - * Tests used for evaluation purposes (especially performance measurements). * * @author Thomas Wuerthinger */ -@RunWith(Suite.class) -@Suite.SuiteClasses({ - FractionTest.class, - GeometryScenario.class, - AddingInterfaceTest.class -}) -public class EvalTestSuite { +@Retention(RetentionPolicy.CLASS) +public @interface FieldRedefinitionPolicy { + + RedefinitionPolicy value(); } diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/StructuralTestSuite.java b/dcevm/src/main/java/com/github/dcevm/MethodRedefinitionPolicy.java index 861cbe83..01d17c22 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/structural/StructuralTestSuite.java +++ b/dcevm/src/main/java/com/github/dcevm/MethodRedefinitionPolicy.java @@ -22,24 +22,17 @@ * */ -package com.github.dcevm.test.structural; +package com.github.dcevm; -import org.junit.runner.RunWith; -import org.junit.runners.Suite; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; /** - * Class redefinition tests that do arbitrary structural changes. - * <p/> - * TODO: Add a test where redefinition triggers classloading (e.g. because a super type is not yet loaded). * * @author Thomas Wuerthinger */ -@RunWith(Suite.class) -@Suite.SuiteClasses({ - RedefineClassClassTest.class, - RedefineObjectClassTest.class, - InterfaceTest.class, - ThisTypeChange.class -}) -public class StructuralTestSuite { +@Retention(RetentionPolicy.CLASS) +public @interface MethodRedefinitionPolicy { + RedefinitionPolicy value(); + } diff --git a/dcevm/src/test/java7/com/github/dcevm/test/fields/FieldsTestSuite.java b/dcevm/src/main/java/com/github/dcevm/RedefinitionPolicy.java index 9c431dbf..f56ba80a 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/fields/FieldsTestSuite.java +++ b/dcevm/src/main/java/com/github/dcevm/RedefinitionPolicy.java @@ -22,28 +22,15 @@ * */ -package com.github.dcevm.test.fields; - -import org.junit.runner.RunWith; -import org.junit.runners.Suite; +package com.github.dcevm; /** - * Class redefinition tests that may change the methods and fields of class, but do not change the superklass or the implemented - * interface. * * @author Thomas Wuerthinger */ -@RunWith(Suite.class) -@Suite.SuiteClasses({ - FieldChangedOrderTest.class, - FieldModificationTest.class, - ObjectStressTest.class, - YieldTest.class, - ComplexFieldTest.class, - FieldAlignmentTest.class, - StringFieldTest.class, - RedefinePrivateFieldTest.class, - EnumTest.class -}) -public class FieldsTestSuite { +public enum RedefinitionPolicy { + StaticCheck, + DynamicCheck, + AccessDeletedMembers, + AccessOldMembers } diff --git a/dcevm/src/main/java/com/github/dcevm/TestClassAdapter.java b/dcevm/src/main/java/com/github/dcevm/TestClassAdapter.java index aadf1b22..dfde5e52 100644 --- a/dcevm/src/main/java/com/github/dcevm/TestClassAdapter.java +++ b/dcevm/src/main/java/com/github/dcevm/TestClassAdapter.java @@ -23,9 +23,9 @@ */ package com.github.dcevm; -import org.objectweb.asm.ClassVisitor; -import org.objectweb.asm.MethodVisitor; +import org.objectweb.asm.*; import org.objectweb.asm.commons.Remapper; +import org.objectweb.asm.commons.RemappingAnnotationAdapter; import org.objectweb.asm.commons.RemappingClassAdapter; import org.objectweb.asm.commons.RemappingMethodAdapter; @@ -79,8 +79,7 @@ public class TestClassAdapter extends RemappingClassAdapter { protected MethodVisitor createRemappingMethodAdapter( int access, String newDesc, - MethodVisitor mv) - { + MethodVisitor mv) { return new RemappingMethodAdapter(access, newDesc, mv, remapper) { @Override public void visitMethodInsn(int opcode, String owner, String name, String desc) { @@ -97,5 +96,40 @@ public class TestClassAdapter extends RemappingClassAdapter { int pos = name.indexOf(METHOD_SUFFIX); return (pos != -1) ? name.substring(0, pos) : name; } + + @Override + public AnnotationVisitor visitAnnotation(final String desc, final boolean visible) { + AnnotationVisitor av = super.visitAnnotation(remapper.mapDesc(desc), visible); + return av == null ? null : new RemappingAnnotationAdapter(av, remapper) { + @Override + public void visitEnum(String name, String enumDesc, String value) { + if (Type.getType(enumDesc).getClassName().equals(RedefinitionPolicy.class.getName())) { + RedefinitionPolicy valueAsEnum = RedefinitionPolicy.valueOf(value); + if (Type.getType(desc).getClassName().equals(FieldRedefinitionPolicy.class.getName())) { + cv.visitAttribute(new SingleByteAttribute(FieldRedefinitionPolicy.class.getSimpleName(), (byte) valueAsEnum.ordinal())); + } + if (Type.getType(desc).getClassName().equals(MethodRedefinitionPolicy.class.getName())) { + cv.visitAttribute(new SingleByteAttribute(MethodRedefinitionPolicy.class.getSimpleName(), (byte) valueAsEnum.ordinal())); + } + } + super.visitEnum(name, desc, value); + } + }; + } + + private static class SingleByteAttribute extends Attribute { + private byte value; + + public SingleByteAttribute(String name, byte value) { + super(name); + this.value = value; + } + + @Override + protected ByteVector write(ClassWriter writer, byte[] code, int len, int maxStack, int maxLocals) { + return new ByteVector().putByte(value); + } + } + } diff --git a/dcevm/src/test/java7/com/github/dcevm/test/LightTestSuite.java b/dcevm/src/test/java7/com/github/dcevm/test/LightTestSuite.java deleted file mode 100644 index 5e6633d6..00000000 --- a/dcevm/src/test/java7/com/github/dcevm/test/LightTestSuite.java +++ /dev/null @@ -1,49 +0,0 @@ -/* - * 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. - * - * 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.github.dcevm.test; - -import com.github.dcevm.test.body.BodyTestSuite; -import com.github.dcevm.test.eval.EvalTestSuite; -import com.github.dcevm.test.fields.FieldsTestSuite; -import com.github.dcevm.test.methods.MethodsTestSuite; -import com.github.dcevm.test.structural.StructuralTestSuite; -import org.junit.runner.RunWith; -import org.junit.runners.Suite; - -/** - * Summarizes all available test suites. - * - * @author Thomas Wuerthinger - */ -@RunWith(Suite.class) -@Suite.SuiteClasses({ - BodyTestSuite.class, - EvalTestSuite.class, - MethodsTestSuite.class, - FieldsTestSuite.class, - StructuralTestSuite.class -}) -public class LightTestSuite { -} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/TestUtil.java b/dcevm/src/test/java7/com/github/dcevm/test/TestUtil.java index 0d88d843..e5ee6bab 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/TestUtil.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/TestUtil.java @@ -33,8 +33,7 @@ import com.github.dcevm.HotSwapTool; * @author Thomas Wuerthinger */ public class TestUtil { - - public static final boolean LIGHT = true; + public static final boolean LIGHT = Boolean.getBoolean("dcevm.test.light"); public static int assertException(Class exceptionClass, Runnable run) { @@ -63,15 +62,6 @@ public class TestUtil { return assertException(UnsupportedOperationException.class, run); } - public static void assertUnsupportedToVersion(final Class clazz, final int version) { - TestUtil.assertUnsupported(new Runnable() { - @Override - public void run() { - HotSwapTool.toVersion(clazz, version); - } - }); - } - public static void assertUnsupportedToVersionWithLight(final Class clazz, final int version) { TestUtil.assertUnsupportedWithLight(new Runnable() { @Override diff --git a/dcevm/src/test/java7/com/github/dcevm/test/body/BodyTestSuite.java b/dcevm/src/test/java7/com/github/dcevm/test/body/BodyTestSuite.java deleted file mode 100644 index d6d687a8..00000000 --- a/dcevm/src/test/java7/com/github/dcevm/test/body/BodyTestSuite.java +++ /dev/null @@ -1,53 +0,0 @@ -/* - * 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. - * - * 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.github.dcevm.test.body; - -import org.junit.runner.RunWith; -import org.junit.runners.Suite; - -/** - * Class redefinition tests that swap only method bodies and change nothing else. This test cases should also - * run with the current version of HotSpot. - * - * @author Thomas Wuerthinger - */ -@RunWith(Suite.class) -@Suite.SuiteClasses( - { - StaticTest.class, - SimpleStaticTest.class, - MultipleThreadsTest.class, - OldActivationTest.class, - RefactorActiveMethodTest.class, - StressTest.class, - FacTest.class, - FibTest.class, - RedefinePrivateMethodTest.class, - ClassRenamingTestCase.class, - EMCPTest.class, - ArrayTest.class - }) -public class BodyTestSuite { -} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/body/StaticTest.java b/dcevm/src/test/java7/com/github/dcevm/test/body/StaticTest.java index 8b1300c2..29a5ecdf 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/body/StaticTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/body/StaticTest.java @@ -30,9 +30,9 @@ import org.junit.Test; import java.util.ArrayList; import java.util.List; -import static junit.framework.Assert.assertNull; import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static junit.framework.Assert.assertNull; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertTrue; diff --git a/dcevm/src/test/java7/com/github/dcevm/test/category/Full.java b/dcevm/src/test/java7/com/github/dcevm/test/category/Full.java new file mode 100644 index 00000000..6bc8bfb2 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/category/Full.java @@ -0,0 +1,7 @@ +package com.github.dcevm.test.category; + +/** + * Tests which are only supported by full flavor of DCEVM. + */ +public interface Full { +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/category/Light.java b/dcevm/src/test/java7/com/github/dcevm/test/category/Light.java new file mode 100644 index 00000000..d18e68fc --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/category/Light.java @@ -0,0 +1,8 @@ +package com.github.dcevm.test.category; + +/** + * Tests which are only supported by light flavor of DCEVM (for example, tests verifying certain + * operation is prohibited on light flavor). + */ +public interface Light { +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/fields/AccessDeletedFieldTest.java b/dcevm/src/test/java7/com/github/dcevm/test/fields/AccessDeletedFieldTest.java new file mode 100644 index 00000000..d66cfa6d --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/fields/AccessDeletedFieldTest.java @@ -0,0 +1,193 @@ +/*
+ * 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.
+ *
+ * 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.github.dcevm.test.fields;
+
+import com.github.dcevm.test.TestUtil;
+import org.junit.Before;
+import org.junit.Test;
+
+import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__;
+import static com.github.dcevm.test.util.HotSwapTestHelper.__version__;
+import static org.junit.Assert.assertEquals;
+
+/**
+ * Tests for accessing a deleted field. In the first scenario, the field is deleted from the class.
+ * In the second scenario, it is deleted because of a changed subtype relationship.
+ *
+ * @author Thomas Wuerthinger
+ */
+public class AccessDeletedFieldTest {
+
+ @Before
+ public void setUp() throws Exception {
+ __toVersion__(0);
+ }
+
+ // Version 0
+ public static class A {
+
+ public int x;
+
+ int getFieldInOldCode() {
+
+ __toVersion__(1);
+
+ // This field does no longer exist
+ return x;
+ }
+ }
+
+ public static class B extends A {
+ }
+
+ // Version 1
+ public static class A___1 {
+ }
+
+ // Version 2
+ public static class B___2 {
+ }
+
+ // Method to enforce cast (otherwise bytecodes become invalid in version 2)
+ public static A convertBtoA(Object b) {
+ return (A) b;
+ }
+
+ @Test
+ public void testOldCodeAccessesDeletedField() {
+
+ assert __version__() == 0;
+
+ final A a = new A();
+ a.x = 1;
+
+ TestUtil.assertException(NoSuchFieldError.class, new Runnable() {
+ @Override
+ public void run() {
+ assertEquals(0, a.getFieldInOldCode());
+ }
+ });
+
+ assert __version__() == 1;
+ __toVersion__(0);
+ assertEquals(0, a.x);
+ }
+
+ @Test
+ public void testAccessDeletedField() {
+
+ assert __version__() == 0;
+
+ final A a = new A();
+ a.x = 1;
+
+ assertEquals(1, a.x);
+
+ __toVersion__(1);
+
+ TestUtil.assertException(NoSuchFieldError.class, new Runnable() {
+ @Override
+ public void run() {
+ System.out.println(a.x);
+ }
+ });
+
+ __toVersion__(0);
+ assertEquals(0, a.x);
+ }
+
+ @Test
+ public void testAccessDeleteBaseClassFieldNormal() {
+
+ __toVersion__(0);
+ assert __version__() == 0;
+ final B b = new B();
+ b.x = 1;
+ final A a = new A();
+ a.x = 2;
+
+ assertEquals(1, b.x);
+ assertEquals(2, a.x);
+
+ __toVersion__(2);
+
+ TestUtil.assertException(NoSuchFieldError.class, new Runnable() {
+
+ @Override
+ public void run() {
+ System.out.println(b.x);
+ }
+ });
+
+ assertEquals(2, a.x);
+
+ __toVersion__(0);
+ assertEquals(0, b.x);
+ }
+
+ @Test
+ public void testAccessDeleteBaseClassFieldInvalid() {
+
+ __toVersion__(0);
+ assert __version__() == 0;
+ final B b = new B();
+ final A a1 = new A();
+ a1.x = 1;
+ b.x = 1;
+
+ __toVersion__(2);
+
+ TestUtil.assertException(NoSuchFieldError.class, new Runnable() {
+
+ @Override
+ public void run() {
+ System.out.println(b.x);
+ }
+ });
+
+ assertEquals(1, a1.x);
+
+ __toVersion__(0);
+ assertEquals(0, b.x);
+ assertEquals(1, a1.x);
+
+ A a = convertBtoA(b);
+
+ assertEquals(0, b.x);
+
+ // Must fail, because now an instance of B is in a local variable of type A!
+ TestUtil.assertException(UnsupportedOperationException.class, new Runnable() {
+
+ @Override
+ public void run() {
+ __toVersion__(2);
+ }
+ });
+
+ assertEquals(0, a.x);
+
+ // Still at version 0
+ assert __version__() == 0;
+ }
+}
diff --git a/dcevm/src/test/java7/com/github/dcevm/test/fields/AccessDeletedStaticFieldTest.java b/dcevm/src/test/java7/com/github/dcevm/test/fields/AccessDeletedStaticFieldTest.java new file mode 100644 index 00000000..13be2e5f --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/fields/AccessDeletedStaticFieldTest.java @@ -0,0 +1,123 @@ +/* + * 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. + * + * 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.github.dcevm.test.fields; + +import com.github.dcevm.test.TestUtil; +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Tests for accessing a deleted static field. + * + * @author Thomas Wuerthinger + */ +public class AccessDeletedStaticFieldTest { + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + // Version 0 + public static class A { + + public static int x; + + static int getFieldInOldCode() { + + __toVersion__(1); + + newMethodFromOldCode(); + + // This field does no longer exist + return x; + } + + static int getFieldEMCPMethod() { + __toVersion__(2); + return A.x; + } + } + + // Version 1 + public static class A___1 { + } + + // Version 2 + + public static class A___2 { + + // EMCP to method in version 0 + static int getFieldEMCPMethod() { + __toVersion__(2); + return A.x; + } + } + + private static void newMethodFromOldCode() { + TestUtil.assertException(NoSuchFieldError.class, new Runnable() { + @Override + public void run() { + System.out.println(A.x); + } + }); + } + + @Test + public void testAccessDeletedStaticField() { + + assert __version__() == 0; + + A.x = 1; + assertEquals(1, A.getFieldInOldCode()); + + assert __version__() == 1; + __toVersion__(0); + assertEquals(0, A.x); + + assert __version__() == 0; + } + + + @Test + public void testAccessDeletedStaticFieldFromEMCPMethod() { + + assert __version__() == 0; + TestUtil.assertException(NoSuchFieldError.class, new Runnable() { + @Override + public void run() { + System.out.println(A.getFieldEMCPMethod()); + } + }); + + __toVersion__(0); + assertEquals(0, A.x); + + assert __version__() == 0; + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/AnnotationTest.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/AnnotationTest.java index 64a04a81..3c4d6697 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/methods/AnnotationTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/methods/AnnotationTest.java @@ -26,7 +26,11 @@ package com.github.dcevm.test.methods; import org.junit.Before; import org.junit.Test; -import java.lang.annotation.*; +import java.lang.annotation.Annotation; +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; import java.lang.reflect.Field; import java.lang.reflect.Method; diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/CallDeletedInterfaceMethodTest.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/CallDeletedInterfaceMethodTest.java new file mode 100644 index 00000000..8b7fd79c --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/methods/CallDeletedInterfaceMethodTest.java @@ -0,0 +1,94 @@ +/* + * 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. + * + * 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.github.dcevm.test.methods; + +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Test case that calls an interface method that was deleted through class redefinition. + * + * @author Thomas Wuerthinger + */ +public class CallDeletedInterfaceMethodTest { + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + // Version 0 + public static interface I { + public int foo(); + } + + public static class A implements I { + @Override + public int foo() { + return 1; + } + } + + public static class Helper { + public static int process(I i) { + __toVersion__(1); + return i.foo(); + } + } + + // Version 1 + public static interface I___1 { + + } + + public static class Helper___1 { + public static int process(I i) { + return 2; + } + } + + @Test + public void testOldCodeCallsDeletedInterfaceMethod() { + + assert __version__() == 0; + A a = new A(); + + assertEquals(1, Helper.process(a)); + assert __version__() == 1; + assertEquals(2, Helper.process(a)); + + __toVersion__(0); + + assertEquals(1, Helper.process(a)); + assert __version__() == 1; + assertEquals(2, Helper.process(a)); + + __toVersion__(0); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/CallDeletedMethodTest.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/CallDeletedMethodTest.java new file mode 100644 index 00000000..73c1fdde --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/methods/CallDeletedMethodTest.java @@ -0,0 +1,114 @@ +/*
+ * 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.
+ *
+ * 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.github.dcevm.test.methods;
+
+import com.github.dcevm.MethodRedefinitionPolicy;
+import com.github.dcevm.RedefinitionPolicy;
+import junit.framework.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__;
+import static com.github.dcevm.test.util.HotSwapTestHelper.__version__;
+import static org.junit.Assert.assertEquals;
+
+/**
+ * Test case that calls a virtual method that was deleted through class redefinition.
+ *
+ * @author Thomas Wuerthinger
+ */
+public class CallDeletedMethodTest {
+
+ @Before
+ public void setUp() throws Exception {
+ __toVersion__(0);
+ }
+
+ // Version 0
+ public static class A {
+
+ public int value() {
+ return 5;
+ }
+
+ public int oldMethod() {
+ __toVersion__(1);
+ return deletedMethod();
+ }
+
+ public int deletedMethod() {
+ return 1;
+ }
+ }
+
+ // Version 1
+ @MethodRedefinitionPolicy(RedefinitionPolicy.AccessDeletedMembers)
+ public static class A___1 {
+
+ public int oldMethod() {
+ return 2;
+ }
+ }
+
+ @Test
+ public void testOldCodeCallsDeletedMethod() {
+
+ assert __version__() == 0;
+ A a = new A();
+
+ assertEquals(1, a.oldMethod());
+ assert __version__() == 1;
+ assertEquals(2, a.oldMethod());
+
+ __toVersion__(0);
+
+ assertEquals(1, a.oldMethod());
+ assert __version__() == 1;
+ assertEquals(2, a.oldMethod());
+
+ __toVersion__(0);
+ }
+
+ @Test
+ public void testNewCodeCallsDeletedMethod() {
+
+ assert __version__() == 0;
+
+ A a = new A();
+ assertEquals(5, a.value());
+
+ __toVersion__(1);
+
+ try {
+ a.value();
+ Assert.fail("NoSuchMethodError exception must be thrown!");
+ } catch (NoSuchMethodError e) {
+ // Expected exception
+ }
+
+ __toVersion__(0);
+ assertEquals(5, a.value());
+ }
+}
diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/ClassReflectionTest.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/ClassReflectionTest.java index c539fc5f..19ad9cb3 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/methods/ClassReflectionTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/methods/ClassReflectionTest.java @@ -24,8 +24,8 @@ package com.github.dcevm.test.methods; -import junit.framework.Assert; import com.github.dcevm.test.TestUtil; +import junit.framework.Assert; import org.junit.Before; import org.junit.Test; diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/DeleteActiveMethodTest.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/DeleteActiveMethodTest.java index 065ac632..3a6166f4 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/methods/DeleteActiveMethodTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/methods/DeleteActiveMethodTest.java @@ -1,159 +1,169 @@ -/* - * 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. - * - * 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.github.dcevm.test.methods; - -import junit.framework.Assert; -import com.github.dcevm.test.TestUtil; -import org.junit.Before; -import org.junit.Test; - -import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; -import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; -import static org.junit.Assert.assertEquals; - -/** - * Test cases that delete a method that is currently active on the stack. - * - * @author Thomas Wuerthinger - */ -public class DeleteActiveMethodTest { - - @Before - public void setUp() throws Exception { - __toVersion__(0); - } - - // Version 0 - public static class A { - - boolean firstCall; - - public int value() { - firstCall = true; - return helperValue(); - } - - public int helperValue() { - - if (!firstCall) { - return -1; - } - firstCall = false; - - Thread t = new Thread(new Runnable() { - - @Override - public void run() { - __toVersion__(1); - } - }); - t.start(); - - try { - do { - this.helperValue(); - } while (t.isAlive()); - this.helperValue(); - Assert.fail("Exception expected!"); - } catch (NoSuchMethodError e) { - } - - try { - t.join(); - } catch (InterruptedException e) { - } - - return 1; - } - } - - public static class B { - - public int fac(int x) { - if (x == 0) { - __toVersion__(1); - } - - return x * fac(x - 1); - } - } - - // Version 1 - public static class A___1 { - - boolean firstCall; - - public int value() { - __toVersion__(0); - return 2; - } - } - - public static class B___1 { - } - - @Test - public void testDeleteActiveMethodSimple() { - assert __version__() == 0; - - final B b = new B(); - TestUtil.assertException(NoSuchMethodError.class, new Runnable() { - @Override - public void run() { - b.fac(5); - } - }); - - assert __version__() == 1; - - __toVersion__(0); - assert __version__() == 0; - } - - @Test - public void testDeleteActiveMethod() { - assert __version__() == 0; - - A a = new A(); - - assertEquals(1, a.value()); - assert __version__() == 1; - - assertEquals(2, a.value()); - assert __version__() == 0; - - assertEquals(1, a.value()); - assert __version__() == 1; - - assertEquals(2, a.value()); - assert __version__() == 0; - - assertEquals(1, a.value()); - assert __version__() == 1; - - assertEquals(2, a.value()); - assert __version__() == 0; - } -} +/*
+ * 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.
+ *
+ * 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.github.dcevm.test.methods;
+
+import static org.junit.Assert.assertEquals;
+
+import com.github.dcevm.MethodRedefinitionPolicy;
+import com.github.dcevm.RedefinitionPolicy;
+import com.github.dcevm.test.TestUtil;
+import junit.framework.Assert;
+
+import org.junit.Before;
+import org.junit.Test;
+
+import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__;
+import static com.github.dcevm.test.util.HotSwapTestHelper.__version__;
+
+/**
+ * Test cases that delete a method that is currently active on the stack.
+ *
+ * @author Thomas Wuerthinger
+ */
+public class DeleteActiveMethodTest {
+
+ @Before
+ public void setUp() throws Exception {
+ __toVersion__(0);
+ }
+
+ // Version 0
+ public static class A {
+
+ boolean firstCall;
+
+ public int value() {
+ firstCall = true;
+ return helperValue();
+ }
+
+ public int helperValue() {
+
+ if (!firstCall) {
+ return -1;
+ }
+ firstCall = false;
+
+ Thread t = new Thread(new Runnable() {
+
+ @Override
+ public void run() {
+ __toVersion__(1);
+ }
+ });
+ t.start();
+
+ try {
+ while (t.isAlive()) {
+ try {
+ this.helperValue();
+ Thread.sleep(500);
+ } catch (InterruptedException e) {
+ }
+ helperValue();
+ }
+ Assert.fail("Exception expected!");
+ } catch (NoSuchMethodError e) {
+ }
+
+ try {
+ t.join();
+ } catch (InterruptedException e) {
+ }
+
+ return 1;
+ }
+ }
+
+ public static class B {
+
+ public int fac(int x) {
+ if (x == 0) {
+ __toVersion__(1);
+ }
+
+ return x * fac(x - 1);
+ }
+ }
+
+ // Version 1
+ @MethodRedefinitionPolicy(RedefinitionPolicy.DynamicCheck)
+ public static class A___1 {
+
+ boolean firstCall;
+
+ public int value() {
+ __toVersion__(0);
+ return 2;
+ }
+ }
+
+ @MethodRedefinitionPolicy(RedefinitionPolicy.DynamicCheck)
+ public static class B___1 {
+ }
+
+ @Test
+ public void testDeleteActiveMethodSimple() {
+ assert __version__() == 0;
+
+ final B b = new B();
+ TestUtil.assertException(NoSuchMethodError.class, new Runnable() {
+ @Override
+ public void run() {
+ b.fac(5);
+ }
+ });
+
+ assert __version__() == 1;
+
+ __toVersion__(0);
+ assert __version__() == 0;
+ }
+
+ @Test
+ public void testDeleteActiveMethod() {
+ assert __version__() == 0;
+
+ A a = new A();
+
+ assertEquals(1, a.value());
+ assert __version__() == 1;
+
+ assertEquals(2, a.value());
+ assert __version__() == 0;
+
+ assertEquals(1, a.value());
+ assert __version__() == 1;
+
+ assertEquals(2, a.value());
+ assert __version__() == 0;
+
+ assertEquals(1, a.value());
+ assert __version__() == 1;
+
+ assertEquals(2, a.value());
+ assert __version__() == 0;
+ }
+}
diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/MethodsTestSuite.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/MethodsTestSuite.java deleted file mode 100644 index 2b616ea4..00000000 --- a/dcevm/src/test/java7/com/github/dcevm/test/methods/MethodsTestSuite.java +++ /dev/null @@ -1,49 +0,0 @@ -/* - * 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. - * - * 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.github.dcevm.test.methods; - -import org.junit.runner.RunWith; -import org.junit.runners.Suite; - -/** - * Class redefinition tests that perform adding/removing/changing the methods of a class. - * - * @author Thomas Wuerthinger - */ -@RunWith(Suite.class) -@Suite.SuiteClasses({ - AddMethodTest.class, - DeleteActiveMethodTest.class, - ClassReflectionTest.class, - MethodReflectionTest.class, - ClassObjectSynchronizationTest.class, - ClassObjectHashcodeTest.class, - OverrideMethodTest.class, - SingleClassTest.class, - SingleClassReflectionTest.class, - AnnotationTest.class -}) -public class MethodsTestSuite { -} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/methods/OldCodeNonOSRTest.java b/dcevm/src/test/java7/com/github/dcevm/test/methods/OldCodeNonOSRTest.java new file mode 100644 index 00000000..aa9fbadb --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/methods/OldCodeNonOSRTest.java @@ -0,0 +1,123 @@ +/* + * 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. + * + * 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.github.dcevm.test.methods; + +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Test case that makes sure that old code does not get on-stack-replaced. + * + * @author Thomas Wuerthinger + */ +public class OldCodeNonOSRTest { + + // Chose high enough to make sure method could get OSR (usually the OSR flag in the VM is set to about 15000) + private static final int N = 100000; + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + // Version 0 + public static class A { + + public int value() { + return 5; + } + + public int oldMethod() { + __toVersion__(1); + int sum = 0; + for (int i=0; i<N; i++) { + sum += i; + } + return (sum & deletedMethod()) | 1; + } + + public int oldMethod2() { + int sum = 0; + for (int i=0; i<N; i++) { + sum += i; + } + __toVersion__(1); + return (sum & deletedMethod()) | 1; + } + + public int oldMethod3() { + int sum = 0; + for (int i=0; i<N; i++) { + sum += i; + } + __toVersion__(1); + for (int i=0; i<N; i++) { + sum += i; + } + return (sum & deletedMethod()) | 1; + } + + public int deletedMethod() { + return 1; + } + } + + // Version 1 + public static class A___1 { + + public int oldMethod() { + return 2; + } + } + + @Test + public void testOldCodeNonOSR() { + + assert __version__() == 0; + A a = new A(); + + assertEquals(1, a.oldMethod()); + assert __version__() == 1; + assertEquals(2, a.oldMethod()); + + __toVersion__(0); + + assertEquals(1, a.oldMethod2()); + assert __version__() == 1; + assertEquals(2, a.oldMethod()); + + __toVersion__(0); + + assertEquals(1, a.oldMethod3()); + assert __version__() == 1; + assertEquals(2, a.oldMethod()); + + __toVersion__(0); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/natives/SimpleNativeTest.java b/dcevm/src/test/java7/com/github/dcevm/test/natives/SimpleNativeTest.java new file mode 100644 index 00000000..1873ea60 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/natives/SimpleNativeTest.java @@ -0,0 +1,88 @@ +/* + * 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. + * + * 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.github.dcevm.test.natives; + +import org.junit.Before; +import org.junit.Ignore; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Testing correct resolving of a native method after class redefinition. + * + * @author Thomas Wuerthinger + */ +@Ignore +public class SimpleNativeTest { + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + // Version 0 + public static class A { + + public static int get() { + return value(); + } + + public static native int value(); + } + + // Version 1 + public static class A___1 { + + public static int get() { + return value() + value2(); + } + + public static native int value(); + + public static native int value2(); + } + + @Test + public void testSimpleNativeCalls() { + + assert __version__() == 0; + + + assertEquals(1, A.get()); + + __toVersion__(1); + + assertEquals(3, A.get()); + + __toVersion__(0); + + assertEquals(1, A.get()); + + } + +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/HierarchySwapTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/HierarchySwapTest.java new file mode 100644 index 00000000..e227ab47 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/HierarchySwapTest.java @@ -0,0 +1,397 @@ +/*
+ * 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.
+ *
+ * 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.github.dcevm.test.structural;
+
+import org.junit.Before;
+import org.junit.Ignore;
+import org.junit.Test;
+
+import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__;
+import static com.github.dcevm.test.util.HotSwapTestHelper.__version__;
+import static org.junit.Assert.*;
+
+/**
+ * Smallest test case for a hierarchy swap. A<B is changed to B<A.
+ *
+ * @author Thomas Wuerthinger
+ */
+@Ignore
+public class HierarchySwapTest {
+
+ // Version 0
+ public static class A {
+
+ public int value() {
+ return 1;
+ }
+ }
+
+ public static class B extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class C {
+
+ public boolean doInstanceCheckA(Object o) {
+ return o instanceof A;
+ }
+
+ public boolean doInstanceCheckB(Object o) {
+ return o instanceof B;
+ }
+ }
+
+ public static class Base {
+
+ public String className() {
+ return "Base";
+ }
+ }
+
+ public static class D extends Base {
+
+ @Override
+ public String className() {
+ return "D";
+ }
+
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class E extends Base {
+
+ @Override
+ public String className() {
+ return "E";
+ }
+
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class F extends Base {
+
+ @Override
+ public String className() {
+ return "F";
+ }
+
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ // Version 1
+ public static class A___1 extends B___1 {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class B___1 {
+
+ public int value() {
+ return 4;
+ }
+ }
+
+ public static class C___1 {
+
+ public boolean doInstanceCheckA(Object o) {
+ return o instanceof A;
+ }
+
+ public boolean doInstanceCheckB(Object o) {
+ return o instanceof B;
+ }
+ }
+
+ // Version 2
+ public static class D___2 extends Base {
+
+ @Override
+ public String className() {
+ return "D";
+ }
+
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class E___2 extends D {
+
+ @Override
+ public String className() {
+ return "E";
+ }
+
+ @Override
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class F___2 extends E {
+
+ @Override
+ public String className() {
+ return "F";
+ }
+
+ @Override
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ // Version 3
+ public static class D___3 extends E {
+
+ @Override
+ public String className() {
+ return "D";
+ }
+
+ @Override
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class E___3 extends F {
+
+ @Override
+ public String className() {
+ return "E";
+ }
+
+ @Override
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class F___3 extends Base {
+
+ @Override
+ public String className() {
+ return "F";
+ }
+
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ // Version 4
+ public static class D___4 extends E {
+
+ @Override
+ public String className() {
+ return "D";
+ }
+
+ @Override
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class E___4 extends Base {
+
+ @Override
+ public String className() {
+ return "E";
+ }
+
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ public static class F___4 extends E {
+
+ @Override
+ public String className() {
+ return "F";
+ }
+
+ @Override
+ public String superClassName() {
+ return super.className();
+ }
+ }
+
+ @Before
+ public void setUp() throws Exception {
+ __toVersion__(0);
+ }
+
+ @Test
+ public void testHierarchySwap() {
+
+ assert __version__() == 0;
+
+ A a = new A();
+ B b = new B();
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertTrue(b.getClass().getSuperclass().equals(A.class));
+ assertFalse(a.getClass().getSuperclass().equals(B.class));
+
+ __toVersion__(1);
+
+ assertEquals(8, a.value());
+ assertEquals(4, b.value());
+ assertFalse(b.getClass().getSuperclass().equals(A.class));
+ assertTrue(a.getClass().getSuperclass().equals(B.class));
+
+ __toVersion__(0);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertTrue(b.getClass().getSuperclass().equals(A.class));
+ assertFalse(a.getClass().getSuperclass().equals(B.class));
+ }
+
+ @Test
+ public void testHierarchySwapWithInstanceOfTest() {
+
+ assert __version__() == 0;
+
+ A a = new A();
+ B b = new B();
+ C c = new C();
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertTrue(c.doInstanceCheckA(b));
+ assertFalse(c.doInstanceCheckB(a));
+
+ __toVersion__(1);
+
+ assertEquals(8, a.value());
+ assertEquals(4, b.value());
+ assertFalse(c.doInstanceCheckA(b));
+ assertTrue(c.doInstanceCheckB(a));
+
+ __toVersion__(0);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertTrue(c.doInstanceCheckA(b));
+ assertFalse(c.doInstanceCheckB(a));
+ }
+
+ @Test
+ public void testHierarchySwapWithInstanceOf() {
+
+ assert __version__() == 0;
+
+ A a = new A();
+ B b = new B();
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertTrue(b instanceof A);
+ assertFalse(a instanceof B);
+
+ __toVersion__(1);
+
+ assertEquals(8, a.value());
+ assertEquals(4, b.value());
+ assertFalse(b instanceof A);
+ assertTrue(a instanceof B);
+
+ __toVersion__(0);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertTrue(b instanceof A);
+ assertFalse(a instanceof B);
+ }
+
+ @Test
+ public void testTripleSwap() {
+
+
+ assert __version__() == 0;
+
+ D d = new D();
+ E e = new E();
+ F f = new F();
+
+ assertEquals(d.superClassName(), "Base");
+ assertEquals(e.superClassName(), "Base");
+ assertEquals(f.superClassName(), "Base");
+
+ __toVersion__(2);
+
+ assertEquals(d.superClassName(), "Base");
+ assertEquals(e.superClassName(), "D");
+ assertEquals(f.superClassName(), "E");
+
+ __toVersion__(3);
+
+ assertEquals(d.superClassName(), "E");
+ assertEquals(e.superClassName(), "F");
+ assertEquals(f.superClassName(), "Base");
+
+ __toVersion__(4);
+
+ assertEquals(d.superClassName(), "E");
+ assertEquals(e.superClassName(), "Base");
+ assertEquals(f.superClassName(), "E");
+
+ __toVersion__(3);
+
+ assertEquals(d.superClassName(), "E");
+ assertEquals(e.superClassName(), "F");
+ assertEquals(f.superClassName(), "Base");
+
+ __toVersion__(2);
+
+ assertEquals(d.superClassName(), "Base");
+ assertEquals(e.superClassName(), "D");
+ assertEquals(f.superClassName(), "E");
+
+ __toVersion__(0);
+
+ assertEquals(d.superClassName(), "Base");
+ assertEquals(e.superClassName(), "Base");
+ assertEquals(f.superClassName(), "Base");
+ }
+}
diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/InterfaceTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/InterfaceTest.java index f514373b..7df37490 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/structural/InterfaceTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/InterfaceTest.java @@ -25,7 +25,11 @@ package com.github.dcevm.test.structural; import com.github.dcevm.test.TestUtil; -import org.junit.*; +import org.junit.After; +import org.junit.AfterClass; +import org.junit.Before; +import org.junit.BeforeClass; +import org.junit.Test; import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/LargeHierarchyTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/LargeHierarchyTest.java new file mode 100644 index 00000000..d5ad95de --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/LargeHierarchyTest.java @@ -0,0 +1,293 @@ +/*
+ * 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.
+ *
+ * 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.github.dcevm.test.structural;
+
+import org.junit.Before;
+import org.junit.Test;
+
+import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__;
+import static com.github.dcevm.test.util.HotSwapTestHelper.__version__;
+import static org.junit.Assert.assertEquals;
+
+/**
+ * Tests that modify a large class hierarchy with the classes A, B, C, D, E, and F.
+ *
+ * @author Thomas Wuerthinger
+ */
+public class LargeHierarchyTest {
+
+ private A a = new A();
+ private B b = new B();
+ private C c = new C();
+ private D d = new D();
+ private E e = new E();
+ private F f = new F();
+
+ @Before
+ public void setUp() throws Exception {
+ __toVersion__(0);
+ }
+
+ // Version 0
+ public static class A {
+
+ public int value() {
+ return 1;
+ }
+ }
+
+ public static class B extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class C extends B {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class D extends C {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class E extends D {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class F extends E {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ // Version 1
+ public static class A___1 {
+
+ public int value() {
+ return 2;
+ }
+ }
+
+ // Version 2
+ // D - E - F
+ // /
+ // A - B - C
+ public static class D___2 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ // Version 3
+ // D
+ // /
+ // A - B - C - E - F
+ public static class D___3 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class E___3 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ // Version 4
+ // Completely flat
+ public static class C___4 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class D___4 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class E___4 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ public static class F___4 extends A {
+
+ @Override
+ public int value() {
+ return super.value() * 2;
+ }
+ }
+
+ // Version 5
+ public static class F___5 extends E {
+
+ @Override
+ public int value() {
+ return 0;
+ }
+ }
+
+ @Test
+ public void testChangeBaseClass() {
+
+ assert __version__() == 0;
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(32, f.value());
+
+ __toVersion__(1);
+
+ assertEquals(2, a.value());
+ assertEquals(4, b.value());
+ assertEquals(8, c.value());
+ assertEquals(16, d.value());
+ assertEquals(32, e.value());
+ assertEquals(64, f.value());
+
+ __toVersion__(0);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(32, f.value());
+ }
+
+ @Test
+ public void testChangeSubClass() {
+ assert __version__() == 0;
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(32, f.value());
+
+ __toVersion__(5);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(0, f.value());
+
+ __toVersion__(0);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(32, f.value());
+ }
+
+ @Test
+ public void testChangeHierarchy() {
+
+ assert __version__() == 0;
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(32, f.value());
+
+ __toVersion__(2);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(2, d.value());
+ assertEquals(4, e.value());
+ assertEquals(8, f.value());
+
+ __toVersion__(3);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(2, d.value());
+ assertEquals(2, e.value());
+ assertEquals(4, f.value());
+
+ __toVersion__(4);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(2, c.value());
+ assertEquals(2, d.value());
+ assertEquals(2, e.value());
+ assertEquals(2, f.value());
+
+ __toVersion__(0);
+
+ assertEquals(1, a.value());
+ assertEquals(2, b.value());
+ assertEquals(4, c.value());
+ assertEquals(8, d.value());
+ assertEquals(16, e.value());
+ assertEquals(32, f.value());
+ }
+}
diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineClassClassTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineClassClassTest.java index d0af2372..f3ffb74a 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineClassClassTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineClassClassTest.java @@ -24,9 +24,11 @@ package com.github.dcevm.test.structural; import com.github.dcevm.ClassRedefinitionPolicy; +import com.github.dcevm.test.category.Full; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; +import org.junit.experimental.categories.Category; import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; @@ -36,6 +38,7 @@ import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; * * @author Thomas Wuerthinger */ +@Category(Full.class) @Ignore public class RedefineClassClassTest { diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineObjectClassTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineObjectClassTest.java index 5947be3e..4d36c7e3 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineObjectClassTest.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/RedefineObjectClassTest.java @@ -24,9 +24,11 @@ package com.github.dcevm.test.structural; import com.github.dcevm.ClassRedefinitionPolicy; +import com.github.dcevm.test.category.Full; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; +import org.junit.experimental.categories.Category; import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; @@ -37,113 +39,109 @@ import static org.junit.Assert.assertEquals; * * @author Thomas Wuerthinger */ +@Category(Full.class) @Ignore public class RedefineObjectClassTest { - // Version 0 - public static class Helper { - public static String access(Object o) { - return ""; - } + // Version 0 + public static class Helper { + public static String access(Object o) { + return ""; } + } - // Version 1 + // Version 1 - public static class Helper___1 { - public static String access(Object o) { - return ((A___1) o).myTestFunction___(); - } + public static class Helper___1 { + public static String access(Object o) { + return ((A___1) o).myTestFunction___(); } + } - @ClassRedefinitionPolicy(alias = java.lang.Object.class) - public static class A___1 { + @ClassRedefinitionPolicy(alias = java.lang.Object.class) + public static class A___1 { - public final native Class<? extends Object> getClass___(); + public final native Class<? extends Object> getClass___(); - @Override - public native int hashCode(); + public native int hashCode(); - @Override - public boolean equals(Object obj) { - return (this == obj); - } - - public static int x; - public static int x1; - public static int x2; - public static int x3; - public static int x4; - public static int x5; + public boolean equals(Object obj) { + return (this == obj); + } - @Override - protected native Object clone() throws CloneNotSupportedException; + public static int x; + public static int x1; + public static int x2; + public static int x3; + public static int x4; + public static int x5; - @Override - public String toString() { - System.out.println("x=" + (x++)); - return getClass().getName() + "@" + Integer.toHexString(hashCode());// myTestFunction___(); - } + protected native Object clone() throws CloneNotSupportedException; - public final String myTestFunction___() { - return "com/github/dcevm/test"; - } + public String toString() { + System.out.println("x=" + (x++)); + return getClass().getName() + "@" + Integer.toHexString(hashCode());// myTestFunction___(); + } - public final native void notify___(); + public final String myTestFunction___() { + return "test"; + } - public final native void notifyAll___(); + public final native void notify___(); - public final native void wait___(long timeout) throws InterruptedException; + public final native void notifyAll___(); - public final void wait___(long timeout, int nanos) throws InterruptedException { + public final native void wait___(long timeout) throws InterruptedException; + public final void wait___(long timeout, int nanos) throws InterruptedException { - if (timeout < 0) { - throw new IllegalArgumentException("timeout value is negative"); - } - if (nanos < 0 || nanos > 999999) { - throw new IllegalArgumentException( - "nanosecond timeout value out of range"); - } + if (timeout < 0) { + throw new IllegalArgumentException("timeout value is negative"); + } - if (nanos >= 500000 || (nanos != 0 && timeout == 0)) { - timeout++; - } + if (nanos < 0 || nanos > 999999) { + throw new IllegalArgumentException( + "nanosecond timeout value out of range"); + } - wait(timeout); - } + if (nanos >= 500000 || (nanos != 0 && timeout == 0)) { + timeout++; + } - public final void wait___() throws InterruptedException { - wait(0); - } + wait(timeout); + } - @Override - protected void finalize() throws Throwable { - } + public final void wait___() throws InterruptedException { + wait(0); } - @Before - public void setUp() throws Exception { - __toVersion__(0); + protected void finalize() throws Throwable { } + } - @Test - public void testRedefineObject() { + @Before + public void setUp() throws Exception { + __toVersion__(0); + } - assert __version__() == 0; + @Test + public void testRedefineObject() { - Object o = new Object(); - __toVersion__(1); + assert __version__() == 0; - System.out.println(this.toString()); - System.out.println(o.toString()); - System.out.println(this.toString()); + Object o = new Object(); + __toVersion__(1); + System.out.println(this.toString()); + System.out.println(o.toString()); + System.out.println(this.toString()); - //assertEquals("test", o.toString()); - assertEquals("com/github/dcevm/test", Helper.access(o)); - __toVersion__(0); - __toVersion__(1); - __toVersion__(0); - } + + //assertEquals("test", o.toString()); + assertEquals("test", Helper.access(o)); + __toVersion__(0); + __toVersion__(1); + __toVersion__(0); + } } diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/ThisTypeChange.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/ThisTypeChange.java index bd5de1b1..aaed2e6c 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/structural/ThisTypeChange.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/ThisTypeChange.java @@ -25,8 +25,10 @@ package com.github.dcevm.test.structural; import com.github.dcevm.test.TestUtil; +import com.github.dcevm.test.category.Light; import org.junit.Before; import org.junit.Test; +import org.junit.experimental.categories.Category; import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; @@ -36,6 +38,7 @@ import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; * * @author Thomas Wuerthinger */ +@Category(Light.class) public class ThisTypeChange { @Before diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingHeapTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingHeapTest.java new file mode 100644 index 00000000..d38495d5 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingHeapTest.java @@ -0,0 +1,180 @@ +/* + * 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. + * + * 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.github.dcevm.test.structural; + +import com.github.dcevm.test.TestUtil; +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Test case for type narrowing. + * + * @author Thomas Wuerthinger + */ +public class TypeNarrowingHeapTest { + + // Version 0 + public static class A { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + } + + public static class C { + private A a; + + public C(A a) { + this.a = a; + } + } + + public static class B extends A { + + } + + + // Version 1 + public static class B___1 { + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + A a = new A(); + B b = new B(); + } + + @Test + public void testSimpleTypeNarrowing() { + + assert __version__() == 0; + + A a = convertBtoA(new B()); + + assertEquals(1, a.value()); + + // Cannot do conversion if A object is on the stack! + a = null; + + __toVersion__(1); + + TestUtil.assertException(NoSuchMethodError.class, new Runnable() { + @Override + public void run() { + B b = new B(); + b.value(); + } + }); + + __toVersion__(0); + assert __version__() == 0; + } + + @Test + public void testTypeNarrowingWithField() { + C c = new C(new A()); + + __toVersion__(1); + + __toVersion__(0); + + c = new C(convertBtoA(new B())); + + TestUtil.assertException(UnsupportedOperationException.class, new Runnable() { + @Override + public void run() { + __toVersion__(1); + } + }); + + assert __version__() == 0; + + c.a = null; + + __toVersion__(1); + + __toVersion__(0); + } + + // Method to enforce cast (otherwise bytecodes become invalid in version 2) + public static A convertBtoA(Object b) { + return (A)b; + } + + @Test + public void testTypeNarrowingWithArray() { + final B b = new B(); + final A[] arr = new A[3]; + arr[0] = new A(); + + assert b instanceof A; + + __toVersion__(1); + + assert !(b instanceof A); + + TestUtil.assertException(ArrayStoreException.class, new Runnable() { + @Override + public void run() { + arr[1] = b; + } + }); + + __toVersion__(0); + + arr[1] = new B(); + + TestUtil.assertException(UnsupportedOperationException.class, new Runnable() { + @Override + public void run() { + __toVersion__(1); + } + }); + + assert __version__() == 0; + + assert b instanceof A; + + arr[1] = new A(); + + __toVersion__(1); + + assert !(b instanceof A); + + __toVersion__(0); + + assert b instanceof A; + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest.java new file mode 100644 index 00000000..47d83e6f --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest.java @@ -0,0 +1,113 @@ +/* + * 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. + * + * 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.github.dcevm.test.structural; + +import com.github.dcevm.test.TestUtil; +import org.junit.Before; +import org.junit.Ignore; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; + +/** + * Test case for type narrowing where a non-active method fails verification because of the new hierarchy. + * + * @author Thomas Wuerthinger + */ +@Ignore +public class TypeNarrowingMethodTest { + + // Version 0 + public static class A { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + + public static int badMethod(B b) { + A a = b; + return a.y; + } + } + + public static class B extends A { + + } + + + // Version 1 + public static class B___1 { + } + + // Version 2 + public static class A___2 { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + + public static int badMethod(B b) { + return 5; + } + } + + public static class B___2 { + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + A a = new A(); + B b = new B(); + } + + + @Test + public void testTypeNarrowingWithViolatingMethod() { + + TestUtil.assertException(UnsupportedOperationException.class, new Runnable() { + @Override + public void run() { + __toVersion__(1); + } + }); + + assert __version__() == 0; + + __toVersion__(2); + + __toVersion__(0); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest2.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest2.java new file mode 100644 index 00000000..177b2a7a --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest2.java @@ -0,0 +1,118 @@ +/* + * 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. + * + * 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.github.dcevm.test.structural; + +import com.github.dcevm.test.TestUtil; +import org.junit.Before; +import org.junit.Ignore; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; + +/** + * Test case for type narrowing where a non-active method fails verification because of the new hierarchy. + * + * @author Thomas Wuerthinger + */ +@Ignore +public class TypeNarrowingMethodTest2 { + + // Version 0 + public static class A { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + + public static int badMethod() { + A a = indirectionMethod(); + return a.y; + } + } + + public static class B extends A { + + } + + + // Version 1 + public static class B___1 { + } + + // Version 2 + public static class A___2 { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + + public static int badMethod(B b) { + return 5; + } + } + + public static class B___2 { + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + A a = new A(); + B b = new B(); + } + + public static B indirectionMethod() { + return new B(); + } + + @Test + public void testTypeNarrowingWithViolatingMethod() { + final A a = new A(); + + TestUtil.assertException(UnsupportedOperationException.class, new Runnable() { + @Override + public void run() { + __toVersion__(1); + System.out.println(a.badMethod()); + } + }); + + assert __version__() == 0; + + __toVersion__(2); + + __toVersion__(0); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest3.java b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest3.java new file mode 100644 index 00000000..bf746717 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/structural/TypeNarrowingMethodTest3.java @@ -0,0 +1,117 @@ +/* + * 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. + * + * 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.github.dcevm.test.structural; + +import com.github.dcevm.test.TestUtil; +import org.junit.Before; +import org.junit.Ignore; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; + +/** + * Test case for type narrowing where a non-active method fails verification because of the new hierarchy. + * + * @author Thomas Wuerthinger + */ +@Ignore +public class TypeNarrowingMethodTest3 { + + // Version 0 + public static class A { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + + public static int badMethod() { + A a = indirectionMethod()[0]; + return a.y; + } + } + + public static class B extends A { + + } + + // Version 1 + public static class B___1 { + } + + // Version 2 + public static class A___2 { + + int x = 1; + int y = 2; + int z = 3; + + public int value() { + return x; + } + + public static int badMethod(B b) { + return 5; + } + } + + public static class B___2 { + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + A a = new A(); + B b = new B(); + } + + public static B[] indirectionMethod() { + return new B[]{ new B() }; + } + + @Test + public void testTypeNarrowingWithViolatingMethod() { + final A a = new A(); + + TestUtil.assertException(UnsupportedOperationException.class, new Runnable() { + @Override + public void run() { + __toVersion__(1); + System.out.println(a.badMethod()); + } + }); + + assert __version__() == 0; + + __toVersion__(2); + + __toVersion__(0); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/transformer/BaseClassTransformerTest.java b/dcevm/src/test/java7/com/github/dcevm/test/transformer/BaseClassTransformerTest.java new file mode 100644 index 00000000..ed592f71 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/transformer/BaseClassTransformerTest.java @@ -0,0 +1,100 @@ +/* + * 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. + * + * 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.github.dcevm.test.transformer; + +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +class BaseClass { + public void $transformer() { + transformerExecuted(); + } + + public void transformerExecuted() { + + } +} + +/** + * Tests for executing the transformer of a base class. + * + * @author Thomas Wuerthinger + */ +public class BaseClassTransformerTest { + + // Version 0 + public static class A { + + public int x = 2; + } + + // Version 3 + public static class A___1 extends BaseClass { + + public int x; + + @Override + public void transformerExecuted() { + System.out.println("Transformer of A executing..."); + x = x * 2; + } + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + @Test + public void testSimpleTransformer() { + + assert __version__() == 0; + + A a = new A(); + + assertEquals(2, a.x); + + __toVersion__(1); + + assertEquals(4, a.x); + + __toVersion__(0); + + assertEquals(4, a.x); + + __toVersion__(1); + + assertEquals(8, a.x); + + __toVersion__(0); + + assertEquals(8, a.x); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/transformer/SimpleTransformerTest.java b/dcevm/src/test/java7/com/github/dcevm/test/transformer/SimpleTransformerTest.java new file mode 100644 index 00000000..7c4ece53 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/transformer/SimpleTransformerTest.java @@ -0,0 +1,89 @@ +/* + * 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. + * + * 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.github.dcevm.test.transformer; + +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Tests for executing the transformer of a class. + * + * @author Thomas Wuerthinger + */ +public class SimpleTransformerTest { + + // Version 0 + public static class A { + + public int x = 2; + } + + // Version 3 + public static class A___1 { + + public int x; + + public void $transformer() { + System.out.println("Transformer of A executing..."); + x = x * 2; + } + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + @Test + public void testSimpleTransformer() { + + assert __version__() == 0; + + A a = new A(); + + assertEquals(2, a.x); + + __toVersion__(1); + + assertEquals(4, a.x); + + __toVersion__(0); + + assertEquals(4, a.x); + + __toVersion__(1); + + assertEquals(8, a.x); + + __toVersion__(0); + + assertEquals(8, a.x); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/transformer/StaticConstructorTransformerTest.java b/dcevm/src/test/java7/com/github/dcevm/test/transformer/StaticConstructorTransformerTest.java new file mode 100644 index 00000000..e255156c --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/transformer/StaticConstructorTransformerTest.java @@ -0,0 +1,88 @@ +/* + * 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. + * + * 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.github.dcevm.test.transformer; + +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; + +/** + * @author Kerstin Breiteneder + * @author Christoph Wimberger + */ +public class StaticConstructorTransformerTest { + + //Version 0 + public static class Static_TestClass { + + // remove static --> no fatal error occurs + public static int x = 0; + //public int x = 0; + + static { + System.out.println("Start Static_TestClass Version 0"); + + try { + Thread.sleep(1000); + } catch (InterruptedException ex) { + } + System.out.println("End Static_TestClass Version 0"); + } + } + + //Version 1 + public static class Static_TestClass___1 { + + public int version = 1; + + static { + System.out.println("Static_TestClass Version 1"); + } + + public void $transformer() { + System.out.println(":::::::::transformerExecuted:::::::::::"); + } + } + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + @Test + public void testStaticConstructorTransformerTest() { + + assert __version__() == 0; + try { + Class.forName("at.ssw.hotswap.test.transformer.StaticConstructorTransformerTest$Static_TestClass"); + } catch (ClassNotFoundException ex) { + ex.printStackTrace(); + } + Static_TestClass clazz = new Static_TestClass(); + + __toVersion__(1); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/transformer/StaticTransformerTest.java b/dcevm/src/test/java7/com/github/dcevm/test/transformer/StaticTransformerTest.java new file mode 100644 index 00000000..a43c1386 --- /dev/null +++ b/dcevm/src/test/java7/com/github/dcevm/test/transformer/StaticTransformerTest.java @@ -0,0 +1,87 @@ +/* + * 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. + * + * 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.github.dcevm.test.transformer; + +import org.junit.Before; +import org.junit.Test; + +import static com.github.dcevm.test.util.HotSwapTestHelper.__toVersion__; +import static com.github.dcevm.test.util.HotSwapTestHelper.__version__; +import static org.junit.Assert.assertEquals; + +/** + * Tests for executing the transformer of a class. + * + * @author Thomas Wuerthinger + */ +public class StaticTransformerTest { + + // Version 0 + public static class A { + + public static int x = 2; + } + + // Version 3 + public static class A___1 { + + public static int x; + + public static void $staticTransformer() { + System.out.println("Static transformer of A executing..."); + x = x * 2; + } + } + + + @Before + public void setUp() throws Exception { + __toVersion__(0); + } + + @Test + public void testStaticTransformer() { + + assert __version__() == 0; + + assertEquals(2, A.x); + + __toVersion__(1); + + assertEquals(4, A.x); + + __toVersion__(0); + + assertEquals(4, A.x); + + __toVersion__(1); + + assertEquals(8, A.x); + + __toVersion__(0); + + assertEquals(8, A.x); + } +} diff --git a/dcevm/src/test/java7/com/github/dcevm/test/util/HotSwapTestHelper.java b/dcevm/src/test/java7/com/github/dcevm/test/util/HotSwapTestHelper.java index b6fc4ff0..d7c00841 100644 --- a/dcevm/src/test/java7/com/github/dcevm/test/util/HotSwapTestHelper.java +++ b/dcevm/src/test/java7/com/github/dcevm/test/util/HotSwapTestHelper.java @@ -24,6 +24,7 @@ package com.github.dcevm.test.util; import com.github.dcevm.HotSwapTool; +import sun.reflect.CallerSensitive; /** * Shortcut methods for testing. Methods are named this way to make them more visible in the test code. |