From owner-freebsd-hackers@FreeBSD.ORG Fri Dec 2 22:03:54 2011 Return-Path: Delivered-To: freebsd-hackers@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id E44531065672 for ; Fri, 2 Dec 2011 22:03:54 +0000 (UTC) (envelope-from kabaev@gmail.com) Received: from mail-qw0-f54.google.com (mail-qw0-f54.google.com [209.85.216.54]) by mx1.freebsd.org (Postfix) with ESMTP id 995498FC12 for ; Fri, 2 Dec 2011 22:03:54 +0000 (UTC) Received: by qaea17 with SMTP id a17so92864qae.13 for ; Fri, 02 Dec 2011 14:03:53 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=gamma; h=date:from:to:cc:subject:message-id:in-reply-to:references:x-mailer :mime-version:content-type; bh=T4LLuI7qmdm6oa4+dy2PA31lP/6OqSD826aYzXHIW/w=; b=W4a5ui6giOWDu7FtHFCoL3nhHWoyVcDICAuUostdVPc88mX+d5gx9fKoffzRb6Cxll JNb+bZDVVuOqLoYY6o6TSPnXBANDrWjV7thkoJoR2udXSkb2WI1c6NH4cAAguRv17gHF fr2jWHfqkgNKLDDvL8Sg1Qx77SKKIUsEDHtT8= Received: by 10.224.197.202 with SMTP id el10mr67444qab.39.1322862125289; Fri, 02 Dec 2011 13:42:05 -0800 (PST) Received: from kan.dyndns.org (c-24-63-226-98.hsd1.ma.comcast.net. [24.63.226.98]) by mx.google.com with ESMTPS id ha3sm7937693qab.2.2011.12.02.13.42.03 (version=SSLv3 cipher=OTHER); Fri, 02 Dec 2011 13:42:03 -0800 (PST) Date: Fri, 2 Dec 2011 16:41:57 -0500 From: Alexander Kabaev To: joris dedieu Message-ID: <20111202164157.3058d91d@kan.dyndns.org> In-Reply-To: References: X-Mailer: Claws Mail 3.7.10 (GTK+ 2.24.6; amd64-portbld-freebsd9.0) Mime-Version: 1.0 Content-Type: multipart/signed; micalg=PGP-SHA1; boundary="Sig_/AnY462gKKJBURQGWFx8zbXI"; protocol="application/pgp-signature" Cc: freebsd-hackers Subject: Re: rtld and noexec X-BeenThere: freebsd-hackers@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: Technical Discussions relating to FreeBSD List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Fri, 02 Dec 2011 22:03:55 -0000 --Sig_/AnY462gKKJBURQGWFx8zbXI Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: quoted-printable On Fri, 2 Dec 2011 18:22:57 +0100 joris dedieu wrote: > Hi, >=20 > Here is a patch I use to prevent loading a shared object from a noexec > mountpoint. It's an easy way, I found, after the last root exploit > ((http://seclists.org/fulldisclosure/2011/Nov/452), to enhance the > security of my web servers (with /home, /tmp and /var/tmp mounted with > noexec). >=20 > - the last ftpd/porftpd (libc ?) exploit does not work (indirect use > of rtld via nsswitch) > - the previous rtld security issue should have been more difficult to > use in a noexec context. > - It may help to prevent some miscellaneous usage of common softwares > using dlopen like apache or php. >=20 > I think it also makes sens because loading a shared object sounds like > a kind of "execution". >=20 > What do you think about this patch and the opportunity to open a PR on > this subject? >=20 > Cheers > Joris >=20 >=20 > --- libexec/rtld-elf/rtld.c.orig 2011-12-02 12:09:40.000000000 > +0100 +++ libexec/rtld-elf/rtld.c 2011-12-02 13:45:18.000000000 > +0100 @@ -1123,32 +1123,50 @@ > { > char *pathname; > char *name; > + struct statfs mnt; >=20 > if (strchr(xname, '/') !=3D NULL) { /* Hard coded pathname */ > + name =3D NULL; > if (xname[0] !=3D '/' && !trust) { > _rtld_error("Absolute pathname required for shared object > \"%s\"", xname); > return NULL; > } > if (refobj !=3D NULL && refobj->z_origin) > - return origin_subst(xname, refobj->origin_path); > + pathname =3D origin_subst(xname, refobj->origin_path); > else > - return xstrdup(xname); > + pathname =3D xstrdup(xname); > + } > + else { /* xname is not a path */ > + if (libmap_disable || (refobj =3D=3D NULL) || > + (name =3D lm_find(refobj->path, xname)) =3D=3D NULL) > + name =3D (char *)xname; > + > + dbg(" Searching for \"%s\"", name); > + > + pathname =3D search_library_path(name, ld_library_path); > + if (pathname =3D=3D NULL && refobj !=3D NULL) > + pathname =3D search_library_path(name, refobj->rpath); > + if (pathname =3D=3D NULL) > + pathname =3D search_library_path(name, gethints()); > + if (pathname =3D=3D NULL) > + pathname =3D search_library_path(name, > STANDARD_LIBRARY_PATH); > + } > + > + if (pathname !=3D NULL) { /* noexec mountpoint in pathname */ > + if (statfs(pathname, &mnt) !=3D 0) > + free(pathname); > + else { > + if (mnt.f_flags & MNT_NOEXEC) { > + _rtld_error("noexec violation for shared object > \"%s\"", pathname); > + free(pathname); > + return NULL; > + } > + else > + return pathname; > + } > } >=20 > - if (libmap_disable || (refobj =3D=3D NULL) || > - (name =3D lm_find(refobj->path, xname)) =3D=3D NULL) > - name =3D (char *)xname; > - > - dbg(" Searching for \"%s\"", name); > - > - if ((pathname =3D search_library_path(name, ld_library_path)) !=3D > NULL || > - (refobj !=3D NULL && > - (pathname =3D search_library_path(name, refobj->rpath)) !=3D NULL) > || > - (pathname =3D search_library_path(name, gethints())) !=3D NULL || > - (pathname =3D search_library_path(name, > STANDARD_LIBRARY_PATH)) !=3D NULL) > - return pathname; > - > if(refobj !=3D NULL && refobj->path !=3D NULL) { > _rtld_error("Shared object \"%s\" not found, required by > \"%s\"", name, basename(refobj->path)); > _______________________________________________ 1. There is a race using statfs and then loading the file. 2. We already have the check in do_load_object --=20 Alexander Kabaev --Sig_/AnY462gKKJBURQGWFx8zbXI Content-Type: application/pgp-signature; name=signature.asc Content-Disposition: attachment; filename=signature.asc -----BEGIN PGP SIGNATURE----- Version: GnuPG v2.0.18 (FreeBSD) iD8DBQFO2UYqQ6z1jMm+XZYRAiW3AJ9cEXng9NgR8lO/tWakLY8lqLSK4gCeKys0 lDv9CfGN3HZloh/QXW9szNU= =E56d -----END PGP SIGNATURE----- --Sig_/AnY462gKKJBURQGWFx8zbXI--