-
Bug
-
Resolution: Unresolved
-
P4
-
8, 21
-
generic
-
generic
A DESCRIPTION OF THE PROBLEM :
The javax.management.ImmutableDescriptor class violates the fundamental Java Object contract that states "if two objects are equal according to the equals(Object) method, then calling the hashCode method on each of the two objects must produce the same integer result."
After serialization and deserialization, an ImmutableDescriptor object maintains equality with its original instance (equals() returns true) but produces a different hashCode value. Specifically, the deserialized object returns hashCode() = 0, while the original object returns a non-zero hash code.
This violation can cause serious issues when using ImmutableDescriptor objects in hash-based collections like HashMap, HashSet, etc., leading to unexpected behavior such as inability to retrieve objects that were previously stored.
---------- BEGIN SOURCE ----------
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import javax.management.Descriptor;
import javax.management.ImmutableDescriptor;
public class ImmutableDescriptorSerialTest {
public static void main(String[] args) throws Exception {
Descriptor d = new ImmutableDescriptor("a=aval", "B=Bval", "cC=cCval");
Descriptor d1 = serialize(d);
if (!d.equals(d1)) {
throw new Exception("Deserialized descriptor not equal to original: " +
"\nOriginal: " + d +
"\nDeserialized: " + d1);
}
if (d.hashCode() != d1.hashCode()) {
throw new Exception("Hash code mismatch: " +
d.hashCode() + " vs " + d1.hashCode() +
" for equal descriptors");
}
}
private static <T> T serialize(T x) throws Exception {
ByteArrayOutputStream bout = new ByteArrayOutputStream();
ObjectOutputStream oout = new ObjectOutputStream(bout);
oout.writeObject(x);
oout.close();
byte[] bytes = bout.toByteArray();
ByteArrayInputStream bin = new ByteArrayInputStream(bytes);
ObjectInputStream oin = new ObjectInputStream(bin);
return (T) oin.readObject();
}
}
---------- END SOURCE ----------
The javax.management.ImmutableDescriptor class violates the fundamental Java Object contract that states "if two objects are equal according to the equals(Object) method, then calling the hashCode method on each of the two objects must produce the same integer result."
After serialization and deserialization, an ImmutableDescriptor object maintains equality with its original instance (equals() returns true) but produces a different hashCode value. Specifically, the deserialized object returns hashCode() = 0, while the original object returns a non-zero hash code.
This violation can cause serious issues when using ImmutableDescriptor objects in hash-based collections like HashMap, HashSet, etc., leading to unexpected behavior such as inability to retrieve objects that were previously stored.
---------- BEGIN SOURCE ----------
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import javax.management.Descriptor;
import javax.management.ImmutableDescriptor;
public class ImmutableDescriptorSerialTest {
public static void main(String[] args) throws Exception {
Descriptor d = new ImmutableDescriptor("a=aval", "B=Bval", "cC=cCval");
Descriptor d1 = serialize(d);
if (!d.equals(d1)) {
throw new Exception("Deserialized descriptor not equal to original: " +
"\nOriginal: " + d +
"\nDeserialized: " + d1);
}
if (d.hashCode() != d1.hashCode()) {
throw new Exception("Hash code mismatch: " +
d.hashCode() + " vs " + d1.hashCode() +
" for equal descriptors");
}
}
private static <T> T serialize(T x) throws Exception {
ByteArrayOutputStream bout = new ByteArrayOutputStream();
ObjectOutputStream oout = new ObjectOutputStream(bout);
oout.writeObject(x);
oout.close();
byte[] bytes = bout.toByteArray();
ByteArrayInputStream bin = new ByteArrayInputStream(bytes);
ObjectInputStream oin = new ObjectInputStream(bin);
return (T) oin.readObject();
}
}
---------- END SOURCE ----------
- links to
-
Review(master) openjdk/jdk/25758