Re: dynamic /dev security hole?

Albert Cahalan
2004-08-09T15:54:11Z

On Mon, 2004-08-09 at 09:30, Michael Buesch wrote:
> -----BEGIN PGP SIGNED MESSAGE-----
> Hash: SHA1
>
> Quoting Eric Lammerts <eric@lammerts.org>:
> > Just an idea for a fix for this problem: If udev would change the
> > permissions to 000 and ownership to root.root just before it unlinks
> > the device node, the copy would become useless.
>
> Like this?
> Only compile tested against glibc.

Pretty much, but you must change ownership first to
keep the user from changing the mode back. There are
ways for an evildoer to win this race if you don't
change the ownership first.

Now all we need is revoke() and we're all set.
Ordering: chown, chmod, revoke, unlink

BTW, I'm make revoke() just force re-verification
of file access.

> ===== udev-remove.c 1.31 vs edited =====
> - --- 1.31/udev-remove.c 2004-04-01 04:12:56 +02:00
> +++ edited/udev-remove.c 2004-08-09 15:23:12 +02:00
> @@ -79,6 +79,23 @@
> strfieldcat(filename, dev->name);
>
> info("removing device node '%s'", filename);
> + /* first remove all permissions on the device node.
> + * This fixes a security issue. If the user created
> + * a hard-link to the device node, he can't use this
> + * anymore, if we change permissions.
> + */
> + retval = chmod(filename, 0000);
> + if (retval) {
> + info("chmod(%s, 0000) failed with error '%s'",
> + filename, strerror(errno));
> + // we continue nevertheless.
> + }
> + retval = chown(filename, 0, 0);
> + if (retval) {
> + info("chown(%s, 0, 0) failed with error '%s'",
> + filename, strerror(errno));
> + // we continue nevertheless.
> + }
> retval = unlink(filename);
> if (errno == ENOENT)
> retval = 0;