Date: Tue, 10 Nov 2015 16:23:07 -0800 From: Tim <tim-security@...tinelchicken.org> To: oss-security@...ts.openwall.com Subject: Re: Assign CVE for common-collections remote code execution on deserialisation flaw Hi Moritz, I sincerely appreciate your response and thoughtful explanation. However, I also think you're wrong. ;-) See my premise below. (I tried to keep it reasonably short!) On Tue, Nov 10, 2015 at 01:10:53AM +0100, Moritz Bechler wrote: > ... > > The main problem is that deserialization can easily get you into > executing code paths (either through custom serialization code or other > funny code). Given that the regular deserialization routines allow any > (Serializable) class to be deserialized, you would have to make sure > that cannot happen by any interaction of any code (what, given the sheer > amount of library code in typical java projects, you simply cannot). If > you cannot, you either must refrain from deserializing any untrusted or > privilege-boundary-crossing data or use a whitelisting approach to > reduce the amount of classes you need to check for problems (that of > course still leaves room for error and often is not easily possible as > the code performing the deserialization is buried in libraries or even > the standard library). > > Regarding the issue at hand, it's pretty clear that the involved parties > make different assumptions about whether it should be okay to > deserialize untrusted data and there simply is no way of differentiating > between the two - one Serializable to rule them all. (Standard library > behaviour, OpenJDK, is also a bit frightening, as they, for example, > assume it is okay to call into collection api methods). > > Given that, the only sane advice I have right now is - don't do it at > all. No RMI, JMX, whatever. Of course that is pretty inconvenient. > > This needs to be fixed on a much lower level than commons collections. > Whitelisting might be a mitigation, but right now, e.g. for RMI code you > cannot really do it without patching your JRE. 1. Most vulnerabilities require a "source" of untrusted data, and a "sink" in the code where that data is used unsafely. In my experience, most vulnerabilities are best corrected by making the "sink" safe. For example: output encoding in HTML or prepared statements in SQL. While many people preach input validation (or *gag* "sanitization"), this is not how most classes of bugs are fixed reliably. 2. There's absolutely no reason serialization can't be done safely. It's absurd to think otherwise, given the fact that developers regularly serialize/marshal/pickle objects into a wide variety of formats, accept these from untrusted sources, deserialize them and aren't made vulnerable by it. Examples: JSON from websites, XML in SOAP, ... Any advice telling developers that "you shouldn't deserialized objects from untrusted sources" must apply only to software that has a flawed deserialization design. 3. Java *does* provide a way to distinguish those to be trusted during deserialization from all other classes. Trusted classes implement Serializable. If you implement Serializable, you've been added to a white list of code that should be safe. If you've added a "sink" to your Serializable objects, then that's a vulnerability. Not only is it a "sink", but validating the input prior to deserialization is nearly impossible, which means you can't filter it at the "source" even if you wanted to. As you mentioned, there's a difference in assumptions. I feel it is very important that the security community speak with one voice when it comes to these underlying assumptions. (Shich is why I spent so much time on this email.) This failure perhaps stems from Commons developers believing that Java serialization is inherently unsafe anyway and therefore no one should ever receive serialized objects from outside their control. This is untrue. We can do serialization safely. Also, we've seen that many applications rely on deserialization to be safe. That is, "in the real world", people use this stuff all the time. You can't just go and make all of it unsafe based on a limited, rigid view of the world. Does Java make it hard to do serialization safely? Sure. Should we avoid accepting serialized objects because of the history of abuse? Yes, probably. But does that mean you can go around adding execution sinks to your library and feel ok about it? Absolutely NOT. That's irresponsible and naive.* So I do agree with you that Oracle could do a much better job here. They could give us better tools and better ways to whitelist the kinds of objects we're willing to accept. Good luck convincing them of that. Last I checked, they still think XMLDecoder is ok. Best regards, tim * Other code that falls into this irresponsible and naive category: - Java's XMLDecoder which doesn't require objects be Serializable (!) - Ruby's session management. While objects are signed, theft of the signing key leads to object forgery, which leads to deserialization RCE. RCE is just one directory traversal away! - Apache Struts HTTP request parsing, which invents a whole new serialized, executable syntax to shoot us in the foot with.
Powered by blists - more mailing lists
Please check out the Open Source Software Security Wiki, which is counterpart to this mailing list.
Confused about mailing lists and their use? Read about mailing lists on Wikipedia and check out these guidelines on proper formatting of your messages.