mirror of
https://github.com/darlinghq/darling-openjdk.git
synced 2024-11-26 22:00:25 +00:00
8234836: Improve serialization handling
Reviewed-by: skoivu, rhalade, chegar
This commit is contained in:
parent
e6364a020e
commit
62da722d66
@ -49,6 +49,7 @@ import static java.io.ObjectStreamClass.processQueue;
|
||||
import jdk.internal.access.SharedSecrets;
|
||||
import jdk.internal.misc.Unsafe;
|
||||
import sun.reflect.misc.ReflectUtil;
|
||||
import sun.security.action.GetBooleanAction;
|
||||
|
||||
/**
|
||||
* An ObjectInputStream deserializes primitive data and objects previously
|
||||
@ -294,6 +295,23 @@ public class ObjectInputStream
|
||||
/** queue for WeakReferences to audited subclasses */
|
||||
static final ReferenceQueue<Class<?>> subclassAuditsQueue =
|
||||
new ReferenceQueue<>();
|
||||
|
||||
/**
|
||||
* Property to permit setting a filter after objects
|
||||
* have been read.
|
||||
* See {@link #setObjectInputFilter(ObjectInputFilter)}
|
||||
*/
|
||||
static final boolean SET_FILTER_AFTER_READ =
|
||||
privilegedGetProperty("jdk.serialSetFilterAfterRead");
|
||||
|
||||
private static boolean privilegedGetProperty(String theProp) {
|
||||
if (System.getSecurityManager() == null) {
|
||||
return Boolean.getBoolean(theProp);
|
||||
} else {
|
||||
return AccessController.doPrivileged(
|
||||
new GetBooleanAction(theProp));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1315,6 +1333,10 @@ public class ObjectInputStream
|
||||
serialFilter != ObjectInputFilter.Config.getSerialFilter()) {
|
||||
throw new IllegalStateException("filter can not be set more than once");
|
||||
}
|
||||
if (totalObjectRefs > 0 && !Caches.SET_FILTER_AFTER_READ) {
|
||||
throw new IllegalStateException(
|
||||
"filter can not be set after an object has been read");
|
||||
}
|
||||
this.serialFilter = filter;
|
||||
}
|
||||
|
||||
|
@ -50,8 +50,10 @@ import org.testng.annotations.Test;
|
||||
import org.testng.annotations.DataProvider;
|
||||
|
||||
/* @test
|
||||
* @bug 8234836
|
||||
* @build SerialFilterTest
|
||||
* @run testng/othervm SerialFilterTest
|
||||
* @run testng/othervm -Djdk.serialSetFilterAfterRead=true SerialFilterTest
|
||||
*
|
||||
* @summary Test ObjectInputFilters
|
||||
*/
|
||||
@ -75,6 +77,10 @@ public class SerialFilterTest implements Serializable {
|
||||
*/
|
||||
private static final Object otherObject = Integer.valueOf(0);
|
||||
|
||||
// Cache value of jdk.serialSetFilterAfterRead property.
|
||||
static final boolean SET_FILTER_AFTER_READ =
|
||||
Boolean.getBoolean("jdk.serialSetFilterAfterRead");
|
||||
|
||||
/**
|
||||
* DataProvider for the individual patterns to test.
|
||||
* Expand the patterns into cases for each of the Std and Compatibility APIs.
|
||||
@ -308,6 +314,45 @@ public class SerialFilterTest implements Serializable {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* After reading some objects from the stream, setting a filter is disallowed.
|
||||
* If the filter was allowed to be set, it would have unpredictable behavior.
|
||||
* Objects already read would not be checked again, including class descriptors.
|
||||
*
|
||||
* Note: To mitigate possible incompatibility a system property can be set
|
||||
* to revert to the old behavior but it re-enables the incorrect use.
|
||||
*/
|
||||
@Test
|
||||
static void testNonSettableAfterReadObject() throws IOException, ClassNotFoundException {
|
||||
String expected1 = "text1";
|
||||
String expected2 = "text2";
|
||||
byte[] bytes = writeObjects(expected1, expected2);
|
||||
|
||||
for (boolean toggle: new boolean[] {true, false}) {
|
||||
try (ByteArrayInputStream bais = new ByteArrayInputStream(bytes);
|
||||
ObjectInputStream ois = new ObjectInputStream(bais)) {
|
||||
Object actual1 = toggle ? ois.readObject() : ois.readUnshared();
|
||||
Assert.assertEquals(actual1, expected1, "unexpected string");
|
||||
// Attempt to set filter
|
||||
ois.setObjectInputFilter(new ObjectInputFilter() {
|
||||
@Override
|
||||
public Status checkInput(FilterInfo filterInfo) {
|
||||
return null;
|
||||
}
|
||||
});
|
||||
if (!SET_FILTER_AFTER_READ)
|
||||
Assert.fail("Should not be able to set filter after readObject has been called");
|
||||
} catch (IllegalStateException ise) {
|
||||
// success, the exception was expected
|
||||
if (SET_FILTER_AFTER_READ)
|
||||
Assert.fail("With jdk.serialSetFilterAfterRead property set = true; " +
|
||||
"should be able to set the filter after a read");
|
||||
} catch (EOFException eof) {
|
||||
Assert.fail("Should not reach end-of-file", eof);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Test that if an Objects readReadResolve method returns an array
|
||||
* that the callback to the filter includes the proper array length.
|
||||
|
Loading…
Reference in New Issue
Block a user