To those who follow this blog for details about Sam, this post isn’t for you.
So, today at work, a co-worker sends an email saying that ‘ps’ is segfaulting whenever it’s run. This is usually a very bad sign (since it frequently means that you’ve been hacked, and a rootkit has been installed). So I start digging around.
Top runs just fine. Shows everything that’s running. I check the md5sum of the ps binary against another machine (presumed to be good), and notice that it’s different… oh boy… that’s a really bad sign. Oh, and the rpm database is corrupted beyond repair.
So I start checking the md5sums of lots of other binaries in /bin, /sbin, /usr/bin and /usr/sbin, etc. And LOTS of binaries have different… so many that it takes me quite a while to find one that ISN’T different… even /bin/true is different, I mean /bin/true???
So, I find three freshly installed boxes, and do the md5sum trick against all their binaries, and I find that of the 4200ish binaries out there, 27ooish of them have different md5sums from the same binary on a different host… but the RPM database swears up and down that the checksums are right.
Turns out that RedHat in their infinate wisdom has turned on the prelinker. This shoves each library into a randomized place in the virtual memory, and modifies the binaries in place so that they know where these libraries are. This is done for two reasons: 1) since the binary has a cashed clue as to where the libary lives in virtual memory, it’s much faster to load it. 2) This also is a nice layer of defence against buffer overflows… they’re somewhat harder to exploit if the bits of memory you want to overflow into are randomized.
Somehow, in ways that I don’t understand as yet, the prelinker also informs the RPM database of the changed checksum and ‘rpm -V’ doesn’t complain about them, but tripwire would (if you’re using tripwire).
The prelinker is actually an interesting idea, but the problem is that it violates a key assumption most sysadmin’s will have about the OS, which is ‘take a system binary (say ‘/usr/bin/find’ for example) and compare the md5sum of it between two machines of identical patch level, and we’d assume the md5sum would be equal for them’. This assumption lies at the heart of how tripwire works. It also would force you to have seperate tripwire read-only media per host you have installed. Oh, and you need to update that read-only memory every 14 days by default, because prelink changes the randomized locations every 14 days (and therefore re-writes the binaries).
But on the plus side, all three Unix admins learned something new today, which doesn’t happen very often.
This affects RedHat AS 4 and 5 and ES 4 and 5 (And CentOS and Oracle Unbreakable Linux).