Tuesday, July 9

Item 76: Write readObject methods defensively


Item 76: Write readObject methods defensively



When does readObject() method comes in picture?

Method is  invoked when and serialized object is deserialized. 

Now Why does it say that readobject method should be written defensively. 

Lets understand how deserialization works. That would help understand Why it says so. 

As a result of deserialization serialized data stream of java instance is unmarshled back into the java object and brought back into the JVM. To create this object readObject method is invoked. Now what is the guarantee that after deserialization we would get logically same instance as it was persisted at the time of serialization. The data stream can bbe tempered . Attacker might modify the stream data which might result into different state of object after deserialization than what it was at the time of serialization. 

Lets take an example : 

Public final class Product  implements Serializable{
final Date date=new date();

}

Now if you serialize an instance of this class ,object will be persisted with data stream having Date variable having value of current date . If attacker temper the stream in such a way that it modify the data value in stream and then deserialzed instance have different date . Now on object constructed after deserialization delete method is invoked to delete all entries prior to the parameterized date. Now actual program had to remove the records prior to date value stored in Product instance at the time of serialization But attacker has tempered that value and it causes different set of records get deleted. 

This is just an simple example . An attacker can perform endless malicious things with data stream . So we need to safeguard that .

how can we do that? 

readObject() method comes to our safety here. This method is invoked to deserialized the instance . We can validate the data of deserialized instance and perform some checks and operations to create a instance with valid set of data. mutable data of immutable Product class i.e. date , that gets tempered by attacker should be validated against date value stored in final date variable and if it is changed method should set it back to correct value .

So we may apply required checks of mutable data of deserializing instance.We can also through exception instead of letting instance created , if we find that data of stream is not valid to create instance back. 

So readObject method should defensively assign the actual value to mutable variables of deserializing instance and prevent hazardous attacks on the program. 

So the only reason Why readObject() method should be written defensively is to ensure the security and validity of instance getting deserialized. 

Please do remember ,any inconsistency or invariants you find in deserializing instance readObject gives you a great opportunity to remove all abberations and create a proper valid instance.

please share your comments/question to discuss it further
-->

No comments:

Post a Comment