11ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson/* 21ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * Copyright (C) 2011 The Android Open Source Project 31ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * 41ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * Licensed under the Apache License, Version 2.0 (the "License"); 51ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * you may not use this file except in compliance with the License. 61ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * You may obtain a copy of the License at 71ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * 81ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * http://www.apache.org/licenses/LICENSE-2.0 91ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * 101ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * Unless required by applicable law or agreed to in writing, software 111ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * distributed under the License is distributed on an "AS IS" BASIS, 121ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 131ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * See the License for the specific language governing permissions and 141ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson * limitations under the License. 151ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson */ 161ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson 171ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilsonpackage libcore.java.io; 181ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson 19738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fullerimport junit.framework.TestCase; 20738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 2147f29998eae296ad812d697c8da12e84e394fee2Jesse Wilsonimport java.io.InvalidClassException; 22738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fullerimport java.io.InvalidObjectException; 2355848681427721532161c63b43b3f99e912d071cNeil Fullerimport java.io.NotSerializableException; 2405895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughesimport java.io.ObjectStreamClass; 2505895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughesimport java.io.ObjectStreamField; 261ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilsonimport java.io.Serializable; 27738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fullerimport java.lang.reflect.InvocationHandler; 28738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fullerimport java.lang.reflect.Method; 29b416ef5dc224630af2b9393a15ae120b27e4864aJesse Wilsonimport libcore.util.SerializationTester; 301ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson 311ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilsonpublic final class SerializationTest extends TestCase { 321ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson 331ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson // http://b/4471249 341ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson public void testSerializeFieldMadeTransient() throws Exception { 3505895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes // Does ObjectStreamClass have the right idea? 3605895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes ObjectStreamClass osc = ObjectStreamClass.lookup(FieldMadeTransient.class); 3705895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes ObjectStreamField[] fields = osc.getFields(); 3805895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes assertEquals(1, fields.length); 3905895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes assertEquals("nonTransientInt", fields[0].getName()); 4005895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes assertEquals(int.class, fields[0].getType()); 4105895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes 428f99aa098c6a06b8be788abbca1c1d1060342709Jesse Wilson // this was created by serializing a FieldMadeTransient with a non-0 transientInt 431ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson String s = "aced0005737200346c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e54657" 441ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson + "374244669656c644d6164655472616e7369656e74000000000000000002000149000c7472616e736" 451ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson + "9656e74496e747870abababab"; 46b416ef5dc224630af2b9393a15ae120b27e4864aJesse Wilson FieldMadeTransient deserialized = (FieldMadeTransient) SerializationTester.deserializeHex(s); 471ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson assertEquals(0, deserialized.transientInt); 481ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson } 491ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson 501ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson static class FieldMadeTransient implements Serializable { 511ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson private static final long serialVersionUID = 0L; 52729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller @SuppressWarnings("unused") 531ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson private transient int transientInt; 54729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller @SuppressWarnings("unused") 5505895faacf43e6fd2bcd57baed31832f6888cb31Elliott Hughes private int nonTransientInt; 561ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson } 5747f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson 5855848681427721532161c63b43b3f99e912d071cNeil Fuller public void testSerializeFieldMadeStatic() throws Exception { 5955848681427721532161c63b43b3f99e912d071cNeil Fuller // Does ObjectStreamClass have the right idea? 6055848681427721532161c63b43b3f99e912d071cNeil Fuller ObjectStreamClass osc = ObjectStreamClass.lookup(FieldMadeStatic.class); 6155848681427721532161c63b43b3f99e912d071cNeil Fuller ObjectStreamField[] fields = osc.getFields(); 6255848681427721532161c63b43b3f99e912d071cNeil Fuller assertEquals(0, fields.length); 6355848681427721532161c63b43b3f99e912d071cNeil Fuller 6455848681427721532161c63b43b3f99e912d071cNeil Fuller // This was created by serializing a FieldMadeStatic with a non-static staticInt 6555848681427721532161c63b43b3f99e912d071cNeil Fuller String s = "aced0005737200316c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e54657" 6655848681427721532161c63b43b3f99e912d071cNeil Fuller + "374244669656c644d6164655374617469630000000000000000020001490009737461746963496e7" 6755848681427721532161c63b43b3f99e912d071cNeil Fuller + "47870000022b8"; 6855848681427721532161c63b43b3f99e912d071cNeil Fuller FieldMadeStatic deserialized = (FieldMadeStatic) SerializationTester.deserializeHex(s); 69729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller // The field data must be ignored if it is static. 7055848681427721532161c63b43b3f99e912d071cNeil Fuller assertEquals(9999, deserialized.staticInt); 7155848681427721532161c63b43b3f99e912d071cNeil Fuller } 7255848681427721532161c63b43b3f99e912d071cNeil Fuller 7355848681427721532161c63b43b3f99e912d071cNeil Fuller static class FieldMadeStatic implements Serializable { 7455848681427721532161c63b43b3f99e912d071cNeil Fuller private static final long serialVersionUID = 0L; 7555848681427721532161c63b43b3f99e912d071cNeil Fuller // private int staticInt = 8888; 7655848681427721532161c63b43b3f99e912d071cNeil Fuller private static int staticInt = 9999; 7755848681427721532161c63b43b3f99e912d071cNeil Fuller } 7855848681427721532161c63b43b3f99e912d071cNeil Fuller 79729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller public static boolean serializableContainer1InitializedFlag = false; 80729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller public static boolean unserializable1InitializedFlag = false; 81729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 82729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller public static class Unserializable1 { 83729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static { 84729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller SerializationTest.unserializable1InitializedFlag = true; 85729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 86729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 87729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 88729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static class SerializableContainer1 implements Serializable { 89729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller private static final long serialVersionUID = 0L; 90729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller private Unserializable1 unserializable = null; 91729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 92729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static { 93729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller serializableContainer1InitializedFlag = true; 94729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 95729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 96729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 9755848681427721532161c63b43b3f99e912d071cNeil Fuller // We can serialize an object that has an unserializable field providing it is null. 9855848681427721532161c63b43b3f99e912d071cNeil Fuller public void testDeserializeNullUnserializableField() throws Exception { 9955848681427721532161c63b43b3f99e912d071cNeil Fuller // This was created by creating a new SerializableContainer and not setting the 10055848681427721532161c63b43b3f99e912d071cNeil Fuller // unserializable field. A canned serialized form is used so we can tell if the static 10155848681427721532161c63b43b3f99e912d071cNeil Fuller // initializers were executed during deserialization. 102729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller // SerializationTester.serializeHex(new SerializableContainer1()); 103729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller String s = "aced0005737200386c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e54657" 104729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "3742453657269616c697a61626c65436f6e7461696e65723100000000000000000200014c000e7" 105729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "56e73657269616c697a61626c657400124c6a6176612f6c616e672f4f626a6563743b787070"; 10655848681427721532161c63b43b3f99e912d071cNeil Fuller 107729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(serializableContainer1InitializedFlag); 108729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(unserializable1InitializedFlag); 10955848681427721532161c63b43b3f99e912d071cNeil Fuller 110729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller SerializableContainer1 sc = (SerializableContainer1) SerializationTester.deserializeHex(s); 11155848681427721532161c63b43b3f99e912d071cNeil Fuller assertNull(sc.unserializable); 11255848681427721532161c63b43b3f99e912d071cNeil Fuller 11355848681427721532161c63b43b3f99e912d071cNeil Fuller // Confirm the container was initialized, but the class for the null field was not. 114729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertTrue(serializableContainer1InitializedFlag); 115729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(unserializable1InitializedFlag); 11655848681427721532161c63b43b3f99e912d071cNeil Fuller } 11755848681427721532161c63b43b3f99e912d071cNeil Fuller 118729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static class Unserializable2 { 119729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 12055848681427721532161c63b43b3f99e912d071cNeil Fuller 121729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static class HasUnserializableField implements Serializable { 12255848681427721532161c63b43b3f99e912d071cNeil Fuller private static final long serialVersionUID = 0L; 123729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller @SuppressWarnings("unused") // Required to make objects unserializable. 124729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller private Unserializable2 unserializable = new Unserializable2(); 12555848681427721532161c63b43b3f99e912d071cNeil Fuller } 12655848681427721532161c63b43b3f99e912d071cNeil Fuller 12755848681427721532161c63b43b3f99e912d071cNeil Fuller // We must not serialize an object that has a non-null unserializable field. 12855848681427721532161c63b43b3f99e912d071cNeil Fuller public void testSerializeUnserializableField() throws Exception { 129729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller HasUnserializableField uf = new HasUnserializableField(); 13055848681427721532161c63b43b3f99e912d071cNeil Fuller try { 131729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller SerializationTester.serializeHex(uf); 13255848681427721532161c63b43b3f99e912d071cNeil Fuller fail(); 13355848681427721532161c63b43b3f99e912d071cNeil Fuller } catch (NotSerializableException expected) { 13455848681427721532161c63b43b3f99e912d071cNeil Fuller } 13555848681427721532161c63b43b3f99e912d071cNeil Fuller } 13655848681427721532161c63b43b3f99e912d071cNeil Fuller 137729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller public static boolean serializableContainer2InitializedFlag = false; 138729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 139729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller @SuppressWarnings("unused") // Required for deserialization test 140729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static class SerializableContainer2 implements Serializable { 141729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller private static final long serialVersionUID = 0L; 142729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller private WasSerializable unserializable = null; 143729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 144729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller static { 145729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller serializableContainer2InitializedFlag = true; 146729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 147729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller } 148729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 14955848681427721532161c63b43b3f99e912d071cNeil Fuller // It must not be possible to deserialize an object if a field is no longer serializable. 15055848681427721532161c63b43b3f99e912d071cNeil Fuller public void testDeserializeUnserializableField() throws Exception { 151729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller // This was generated by creating a SerializableContainer2 and setting the unserializable 15255848681427721532161c63b43b3f99e912d071cNeil Fuller // field to a WasSerializable when it was still Serializable. A canned serialized form is 15355848681427721532161c63b43b3f99e912d071cNeil Fuller // used so we can tell if the static initializers were executed during deserialization. 154729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller // SerializableContainer2 sc = new SerializableContainer2(); 15555848681427721532161c63b43b3f99e912d071cNeil Fuller // sc.unserializable = new WasSerializable(); 15655848681427721532161c63b43b3f99e912d071cNeil Fuller // SerializationTester.serializeHex(sc); 157729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller String s = "aced0005737200386c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e54657" 158729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "3742453657269616c697a61626c65436f6e7461696e65723200000000000000000200014c000e7" 159729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "56e73657269616c697a61626c657400334c6c6962636f72652f6a6176612f696f2f53657269616" 160729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "c697a6174696f6e546573742457617353657269616c697a61626c653b7870737200316c6962636" 161729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "f72652e6a6176612e696f2e53657269616c697a6174696f6e546573742457617353657269616c6" 162729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller + "97a61626c65000000000000000002000149000169787000000000"; 163729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller 164729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(serializableContainer2InitializedFlag); 165729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(wasSerializableInitializedFlag); 16655848681427721532161c63b43b3f99e912d071cNeil Fuller try { 16755848681427721532161c63b43b3f99e912d071cNeil Fuller SerializationTester.deserializeHex(s); 16855848681427721532161c63b43b3f99e912d071cNeil Fuller fail(); 16955848681427721532161c63b43b3f99e912d071cNeil Fuller } catch (InvalidClassException expected) { 17055848681427721532161c63b43b3f99e912d071cNeil Fuller } 171729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller // The container class will be initialized to establish the serialVersionUID. 172729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertTrue(serializableContainer2InitializedFlag); 173729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller // Confirm the contained class was initialized. 17455848681427721532161c63b43b3f99e912d071cNeil Fuller assertFalse(wasSerializableInitializedFlag); 17555848681427721532161c63b43b3f99e912d071cNeil Fuller } 17655848681427721532161c63b43b3f99e912d071cNeil Fuller 17747f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson public void testSerialVersionUidChange() throws Exception { 17847f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson // this was created by serializing a SerialVersionUidChanged with serialVersionUID = 0L 17947f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson String s = "aced0005737200396c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e54657" 18047f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson + "3742453657269616c56657273696f6e5569644368616e67656400000000000000000200014900016" 18147f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson + "1787000000003"; 18247f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson try { 18347f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson SerializationTester.deserializeHex(s); 18447f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson fail(); 18547f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } catch (InvalidClassException expected) { 18647f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } 18747f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } 18847f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson 189738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 19047f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson static class SerialVersionUidChanged implements Serializable { 19147f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson private static final long serialVersionUID = 1L; // was 0L 19247f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson private int a; 19347f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } 19447f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson 19547f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson public void testMissingSerialVersionUid() throws Exception { 19647f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson // this was created by serializing a FieldsChanged with one int field named 'a' 19747f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson String s = "aced00057372002f6c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e54657" 19847f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson + "374244669656c64734368616e6765643bcfb934e310fa1c02000149000161787000000003"; 19947f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson try { 20047f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson SerializationTester.deserializeHex(s); 20147f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson fail(); 20247f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } catch (InvalidClassException expected) { 20347f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } 20447f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } 20547f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson 206738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 20747f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson static class FieldsChanged implements Serializable { 20847f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson private int b; // was 'a' 20947f29998eae296ad812d697c8da12e84e394fee2Jesse Wilson } 210738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 211738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static boolean wasSerializableInitializedFlag = false; 212738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 213738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test. 214738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class WasSerializable /* implements java.io.Serializable */ { 215738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static final long serialVersionUID = 0L; 216738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static { 217738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTest.wasSerializableInitializedFlag = true; 218738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 219738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller private int i; 220738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 221738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 222738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeWasSerializableClass() throws Exception { 223738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a WasSerializable when it was serializable. 224738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(new WasSerializable()); 225738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced0005737200316c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6" 226738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "e546573742457617353657269616c697a61626c65000000000000000002000149000169787000000" 227738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "000"; 228738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 229729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(wasSerializableInitializedFlag); 230738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 231738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 232738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 233738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (InvalidClassException expected) { 234738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 235738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller assertFalse(wasSerializableInitializedFlag); 236738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 237738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 238738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // The WasExternalizable class before it was modified. 239738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller /* 240738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class WasExternalizable implements Externalizable { 241738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static final long serialVersionUID = 0L; 242738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 243738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @Override 244738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void readExternal(ObjectInput input) throws IOException, ClassNotFoundException { 245738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 246738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 247738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 248738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @Override 249738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void writeExternal(ObjectOutput output) throws IOException { 250738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 251738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 252738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 253738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller */ 254738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 255738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static boolean wasExternalizableInitializedFlag = false; 256738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 257738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 258738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class WasExternalizable implements Serializable { 259738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static final long serialVersionUID = 0L; 260738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static { 261738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTest.wasExternalizableInitializedFlag = true; 262738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 263738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 264738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 265738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 266738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeWasExternalizableClass() throws Exception { 267738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a WasExternalizable when it was externalizable. 268738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(new WasExternalizable()); 269738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced0005737200336c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6" 270738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "e546573742457617345787465726e616c697a61626c6500000000000000000c0000787078"; 271738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 272729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(wasExternalizableInitializedFlag); 273738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 274738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 275738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 276738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (InvalidClassException expected) { 277738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 278738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Unlike other similar tests static initialization will take place if the local class is 279738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Serializable or Externalizable because serialVersionUID field is accessed. 280738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // The RI appears to do the same. 281738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller assertTrue(wasExternalizableInitializedFlag); 282738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 283738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 284738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // The WasEnum class before it was modified. 285738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller /* 286738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public enum WasEnum { 287738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller VALUE 288738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 289738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller */ 290738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 291738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static boolean wasEnumInitializedFlag = false; 292738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 293738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 294738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class WasEnum { 295738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static final long serialVersionUID = 0L; 296738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static { 297738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTest.wasEnumInitializedFlag = true; 298738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 299738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 300738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 301738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeWasEnum() throws Exception { 302738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a WasEnum when it was an enum. 303738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(WasEnum.VALUE); 304738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced00057e7200296c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6" 305738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "e5465737424576173456e756d00000000000000001200007872000e6a6176612e6c616e672e456e7" 306738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "56d0000000000000000120000787074000556414c5545"; 307738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 308729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(wasEnumInitializedFlag); 309738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 310738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 311738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 312738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (InvalidClassException expected) { 313738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 314738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller assertFalse(wasEnumInitializedFlag); 315738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 316738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 317738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // The WasObject class before it was modified. 318738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller /* 319738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class WasObject implements java.io.Serializable { 320738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static final long serialVersionUID = 0L; 321738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller private int i; 322738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 323738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller */ 324738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 325738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static boolean wasObjectInitializedFlag; 326738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 327738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 328738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public enum WasObject { 329738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller VALUE; 330738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 331738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static { 332738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTest.wasObjectInitializedFlag = true; 333738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 334738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 335738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 336738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeWasObject() throws Exception { 337738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a WasObject when it wasn't yet an enum. 338738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(new WasObject()); 339738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced00057372002b6c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6" 340738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "e54657374245761734f626a656374000000000000000002000149000169787000000000"; 341738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 342729d4ecafff8e6af5a71e4fecb2007917cbc2e2aNeil Fuller assertFalse(wasObjectInitializedFlag); 343738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 344738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 345738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 346738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (InvalidClassException expected) { 347738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 348738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller assertFalse(wasObjectInitializedFlag); 349738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 350738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 351738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 352738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public enum EnumMissingValue { 353738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller /*MISSING_VALUE*/ 354738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 355738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 356738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeEnumMissingValue() throws Exception { 357738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a EnumMissingValue when it had MISSING_VALUE. 358738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(EnumMissingValue.MISSING_VALUE); 359738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced00057e7200326c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6" 360738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "e5465737424456e756d4d697373696e6756616c756500000000000000001200007872000e6a61766" 361738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "12e6c616e672e456e756d0000000000000000120000787074000d4d495353494e475f56414c5545"; 362738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 363738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 364738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 365738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 366738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (InvalidObjectException expected) { 367738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 368738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 369738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 370738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 371738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static Object hasStaticInitializerObject; 372738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 373738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class HasStaticInitializer implements Serializable { 374738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static { 375738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTest.hasStaticInitializerObject = new Object(); 376738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 377738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 378738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 379738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeStaticInitializerIsRunEventually() throws Exception { 380738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a HasStaticInitializer 381738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(new HasStaticInitializer()); 382738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced0005737200366c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6" 383738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "e5465737424486173537461746963496e697469616c697a6572138aa8ed9e9b660a0200007870"; 384738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 385738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Confirm the ClassLoader behaves as it should. 386738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller Class.forName( 387738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller HasStaticInitializer.class.getName(), 388738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller false /* shouldInitialize */, 389738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller Thread.currentThread().getContextClassLoader()); 390738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller assertNull(hasStaticInitializerObject); 391738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 392738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 393738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 394738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller assertNotNull(hasStaticInitializerObject); 395738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 396738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 397738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 398738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static /*interface*/ class WasInterface { 399738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 400738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 401738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 402738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class SerializableInvocationHandler implements InvocationHandler, Serializable { 403738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @Override 404738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public Object invoke(Object proxy, Method method, Object[] args) { 405738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller return null; 406738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 407738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 408738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 409738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeProxyWasInterface() throws Exception { 410738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a proxy referencing WasInterface when it was an 411738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // interface. 412738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Object o = Proxy.newProxyInstance( 413738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Thread.currentThread().getContextClassLoader(), 414738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // new Class[] { WasInterface.class }, 415738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // new SerializableInvocationHandler()); 416738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(o); 417738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced0005737d00000001002e6c6962636f72652e6a6176612e696f2e53657269616c697a6" 418738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "174696f6e5465737424576173496e74657266616365787200176a6176612e6c616e672e7265666c6" 419738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "563742e50726f7879e127da20cc1043cb0200014c0001687400254c6a6176612f6c616e672f72656" 420738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "66c6563742f496e766f636174696f6e48616e646c65723b78707372003f6c6962636f72652e6a617" 421738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "6612e696f2e53657269616c697a6174696f6e546573742453657269616c697a61626c65496e766f6" 422738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "36174696f6e48616e646c6572e6ceffa2941ee3210200007870"; 423738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 424738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 425738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 426738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (ClassNotFoundException expected) { 427738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 428738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 429738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 430738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @SuppressWarnings("unused") // Required for deserialization test 431738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public static class WasSerializableInvocationHandler 432738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller implements InvocationHandler /*, Serializable*/ { 433738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller static final long serialVersionUID = 0L; 434738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 435738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller @Override 436738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public Object invoke(Object proxy, Method method, Object[] args) { 437738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller return null; 438738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 439738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 440738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller 441738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller public void testDeserializeProxyInvocationHandlerWasSerializable() throws Exception { 442738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // This was created by serializing a proxy referencing WasSerializableInvocationHandler when 443738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // it was Serializable. 444738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Object o = Proxy.newProxyInstance( 445738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // Thread.currentThread().getContextClassLoader(), 446738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // new Class[] { Comparable.class }, 447738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // new WasSerializableInvocationHandler()); 448738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller // String s = SerializationTester.serializeHex(o); 449738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller final String s = "aced0005737d0000000100146a6176612e6c616e672e436f6d70617261626c65787200176" 450738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "a6176612e6c616e672e7265666c6563742e50726f7879e127da20cc1043cb0200014c00016874002" 451738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "54c6a6176612f6c616e672f7265666c6563742f496e766f636174696f6e48616e646c65723b78707" 452738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "37200426c6962636f72652e6a6176612e696f2e53657269616c697a6174696f6e546573742457617" 453738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "353657269616c697a61626c65496e766f636174696f6e48616e646c6572000000000000000002000" 454738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller + "07870"; 455738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller try { 456738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller SerializationTester.deserializeHex(s); 457738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller fail(); 458738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } catch (InvalidClassException expected) { 459738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 460738c833d38d41f8f76eb7e77ab39add82b1ae1e2Neil Fuller } 4611ffc4b2e242d1ba40ceb30b21510f0f26bd5aaa2Jesse Wilson} 462