digip.org blog

Jansson 2.6 released

By Petri Lehtinen on 2014-04-01

Jansson 2.6 was released already on 2014-02-11, but I totally forgot to blog about it or even update Jansson's web page. Sorry about that!

Jansson 2.6 is mainly a security release, changing the hash function that is used by Jansson's hashtable implementation. Other changes include minor documentation and build system corrections. For a more comprehensive list of changes, see the release notes.

New hash function

Jansson's old hash function was vulnerable to a denial of service attack. By using specially crafted keys, the attacker could reduce the performance of most object operations. For example, decoding a JSON text with such crafted keys would take tens of seconds for a relatively small file.

Jansson 2.6 changes the hash function to Bob Jenkins' lookup3, which supports seeding. As no non-cryptographic hash function is immune to the key crafting problem, the hash function is seeded by random data when the first JSON object is created, either by explicitly calling json_object(), or by implicitly creating a new object e.g. by decoding a JSON text or calling json_pack().

The purpose of seeding is to make the hash function yield different results on each program run. This makes it virtually impossible to launch a DoS attack anymore.

The hardest part of seeding is how to actually generate random data in a thread-safe manner. Jansson uses /dev/urandom if it's available, or CryptGenRandom() on Windows. If neither are available, a combination of a microsecond precision timestamp and process ID are used as the seed. Seed generation is guarded by architecture dependent lock-free operations to ensure thread safety.

A new function, json_object_seed(), is also exposed, to make it possible for the user to initiate the seeding, e.g. before spawning any threads.