Re: Verbose warning splurged to the log with Secure Coding (dearchiving) -- can they be serious?

Quincey Morris

I think you’re Doing It Wrong™. Your solution is effectively disabling secure coding, which solves your run-time error, but leaves you with the exact security vulnerability that secure coding is supposed to protect against.

Your goal of “I want it to be as flexible as possible” without specifying classes in advance isn’t compatible with secure decoding. 

Let’s stick with your NSDictionary example. There are 3 cases:

1. You (try to) decode the dictionary and specify class NSDictionary. This is insecure, because decoding the dictionary also decodes arbitrary classes contained in the dictionary.

2. The dictionary contains only objects of “plist” classes such as NSNumber, NSDate and standard NS collection classes. There are a finite number of these, so you can always list them all in `decodeObjectOfClasses:forKey:`, and this kind of dictionary is useful for a lot of things without getting into custom classes.

3. The dictionary contains your custom classes and/or client code's custom classes as well. Again, you must use `decodeObjectOfClasses:forKey:` to specify *all* of the classes that might be in the dictionary, but you don’t know them all at compile time.

You can’t do #1, so you must do #2 or #3. Either way, use `decodeObjectOfClasses:forKey:` for a heterogenous collection or hierarchy.

Note that your set of classes for `decodeObjectOfClasses:forKey:` can be built at run-time, but you should avoid the temptation to encode that set into the archive, since that also compromises security. (An attacker can simply ask your code to unarchive data containing malicious classes, and naming their classes!)

If you want to make things flexible for client code, I guess the way to do it would be to have the client tell you, on unarchiving, the list of its custom classes that it allows in the archive. You’d augment that set with the additional classes your own wrapper code needs, and specify that for `decodeObjectOfClasses:forKey:`.

On Feb 24, 2022, at 03:35, Graham Cox <graham@...> wrote:

Well, I figured out a solution, though I’m not sure — it seems slightly smelly, even though it looks neat from the outside and is easy to use. Would appreciate any feedback.

Basically, I walk up the class hierarchy until I hit NSObject, then return the class once removed from that. Then I added a category on NSCoder that uses this to encode that class name in the archive. Using these methods in NSCoding is easy and hides the minor pain involved.

Join { to automatically receive all group messages.