I complete my own answer after a more in-depth comparison between the OSes I am the more familiar with and which have taken quite surprisingly different directions...
PID randomization was popularized by OpenBSD which added it as soon as 1997. At that time it pursued two main goals:
Protect against PID prediction vulnerabilities affecting mostly software which use the PID value to generate temporary file names. This was a common concern at that time, but today I think it would be quite rare to encounter production-level software still not using a proper method.
As a general preventive measure, "If something can be random, make it random.", encompassing putting randomness at several places in the OS (from the IP stack to the memory allocation). While some of the protection resulting from this randomness proved to be useful and became more common, PID randomization has a more troubled history.
As detailed in my question, the cure may be worse than the disease. Due to faster PID reuse, fully random PID may allow remotely exploitable flaws, while sequential PID was mainly known to allow local-only exploits.
As a side note, in an ideal world, all this should not cause any issue (yes, I talk of this ideal world where software is free of bugs and vulnerabilities). In fact these vulnerabilities usually find their root in wrong usage of the PID. Wikipedia defines the PID as being a "number used [...] to uniquely identify an active process". Therefore:
A PID is not designed to build temporary file names. Temporary files are usually created in a shared place, and that means danger! Because of this, temporary files must be created using dedicated functions which will ensure that the three required actions (checking that the file doesn't already exists, create it and set restricted access permissions) are done in an atomic (uninterrupted) way. The C language proposes mkstemp()
and tmpfile()
, and most Unix environments offer a mktemp command to be used by shell scripts, etc.
A PID is not designed to seed a random number generator or generate session ID or cookies. Here again you must refer to your language or environment documentation to get a proper entropy source. On UNIX systems the /dev/urandom
device file is there for this purpose.
It is not by accident that Wikipedia definition explicitly states active process. On some language like C, you stay proprietary of the child process' PID until you wait
for it, but this is not true for all languages (for instance in shell scripts...) and never true for processes which are not your child. In these cases the PID is just a shared resource, and you should remember that this "shared" notion implies "danger", so must therefore ensure that your take proper care and use the right functions designed to match your situation and needs.
Linux
Linux kernel main stream never implemented PID randomization, however this feature was commonly provided for several years through a security oriented third-party patch which finally decided to abandon it.
Around year 2000-2001, several people tried to implement PID randomization for the Linux kernel (examples can be found here and there), however none of these patches were accepted by the kernel development team who rejected them mostly as "security through obscurity".
However, since randomness may actually increase the global security posture of the OS and prevent some attacks, these kernel modifications finally reached their public through the third-party project: grsecurity.
This project started in 2001, bringing several new and advanced security features to the Linux kernel. It allowed to enable/disable randomized PID using a specific sysctl
parameter: kernel.grsecurity.rand_pids
. However, in the late 2006 (I guess - I hate news thread mentioning dates with no year!) they finally decided to drop randomized PID functionality:
grsecurity 2.1.10 was released today for Linux 2.4.34 and 2.6.19.2. Changes in this release include:
- Removal of randomized PIDs feature, since it provides no useful
additional security and wastes memory with the 2.6 kernel's pid bitmap
OpenBSD
OpenBSD having initiated randomized PID functionality, it is still present for historical purposes but has no real security scope nowadays. It is up to the application themselves to ensure they correctly handle fast PID reuse.
OpenBSD aim is to encourage good development practices and thorough code security auditing. That's why they consider that it is not the responsibility of the OS to protect their users against flawed application. On the contrary an application flaw should be detected as soon as possible and corrected in the application instead of remaining hidden by OS ("The sooner we can break it, the sooner we can fix").
As a side note, while such assertion justifies itself for the base OS which is under direct control of the OpenBSD team, this becomes more disputable with third-party software:
However, in this context OpenBSD team makes the assumption that, for a correctly developed and audited software, the PID generation algorithm chosen by the OS must have no impact (neither stability nor security) on the software behavior. If some software is vulnerable to an attack taking advantage of the PID being reused, then it's up to the software to be corrected, and not to the OS to ensure that the PID are not reused too quickly¹.
¹: For the curious, OpenBSD added in 2013 an hardcoded table storing the 100 lastly freed PIDs in order to limit reliability issues on low loaded systems. However, this does not constitutes a security measure since it quickly becomes effectless with higher loads, would this load be caused by genuine activity or as part of an attack.
FreeBSD
FreeBSD provides a sysctl
parameter allowing the administrator to tune the PID generation algorithm from sequential to fully random. It is sequential by default.
FreeBSD implemented random PIDs in 1999 (FreeBSD 4), using OpenBSD as reference, and improved it to let the administrator set a balance between potential issues caused by sequential PID (mostly PID prediction) and potential issues caused by PID randomization (PID reuse and resource consumption).
In fact, FreeBSD design seems quite original since it is not actually the PID which is random, but the PID increment which is a random value taken between 1 and the kern.randompid
parameter:
- If PID randomization is disabled, then the increment will always be 1,
- At maximum this parameter can be set to
PID_MAX
³, in this case the next PID will be fully randomly chosen.
By default PID randomization is disabled (PIDs are generated sequentially). To take effect, the kern.randompid
parameter must be at least greater than 100.
If sequential PID remains a concern, I would personally recommend to set this parameter to a low value like a few hundreds: this should be sufficient to limit trivial PID prediction issues while avoiding more nasty issues caused by PIDs re-use.
³: For the purists it is actually PID_MAX - 100
to cover only non-reserved PID range, it can also be set by using the special value -1
. Out of range values are corrected immediately when setting the sysctl
parameter so no risk to cause any damage here anyway.