PERFORCE change 164668 for review
Robert Watson
rwatson at FreeBSD.org
Thu Jun 18 15:37:10 UTC 2009
http://perforce.freebsd.org/chv.cgi?CH=164668
Change 164668 by rwatson at rwatson_freebsd_capabilities on 2009/06/18 15:36:11
Add lch_start_libs() and lch_startfd_libs(), which allow passing in
specific lists of libraries to be used by sandboxed components.
Affected files ...
.. //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability.h#22 edit
.. //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability_host.c#19 edit
Differences ...
==== //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability.h#22 (text+ko) ====
@@ -30,7 +30,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $P4: //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability.h#21 $
+ * $P4: //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability.h#22 $
*/
#ifndef _LIBCAPABILITY_H_
@@ -40,6 +40,15 @@
struct lc_host;
/*
+ * Description of a library passed to lch_start_libs().
+ */
+struct lc_library {
+ const char *lcl_libpath;
+ const char *lcl_libname;
+ int lcl_fd;
+};
+
+/*
* Capability interfaces.
*/
int lc_limitfd(int fd, cap_rights_t rights);
@@ -55,8 +64,14 @@
*/
int lch_start(const char *sandbox, char *const argv[], u_int flags,
struct lc_sandbox **lcspp);
+int lch_start_libs(const char *sandbox, char *const argv[], u_int flags,
+ struct lc_library *lclp, u_int lcl_count,
+ struct lc_sandbox **lcspp);
int lch_startfd(int fd_sandbox, const char *binname, char *const argv[],
u_int flags, struct lc_sandbox **lcspp);
+int lch_startfd_libs(int fd_sandbox, const char *binname,
+ char *const argv[], u_int flags, struct lc_library *lclp,
+ u_int lcl_count, struct lc_sandbox **lcspp);
void lch_stop(struct lc_sandbox *lcsp);
/*
==== //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability_host.c#19 (text+ko) ====
@@ -30,12 +30,13 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $P4: //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability_host.c#18 $
+ * $P4: //depot/projects/trustedbsd/capabilities/src/lib/libcapability/libcapability_host.c#19 $
*/
#include <sys/param.h>
#include <sys/capability.h>
#include <sys/procdesc.h>
+#include <sys/sbuf.h>
#include <sys/socket.h>
#include <sys/uio.h>
@@ -60,15 +61,13 @@
CAP_MAPEXEC)
#define LIBCAPABILITY_CAPMASK_SANDBOX LIBCAPABILITY_CAPMASK_BIN
#define LIBCAPABILITY_CAPMASK_LDSO LIBCAPABILITY_CAPMASK_BIN
-#define LIBCAPABILITY_CAPMASK_LIBC LIBCAPABILITY_CAPMASK_BIN
-#define LIBCAPABILITY_CAPMASK_LIBCAPABILITY LIBCAPABILITY_CAPMASK_BIN
-#define LIBCAPABILITY_CAPMASK_LIBBZ2 LIBCAPABILITY_CAPMASK_BIN
+#define LIBCAPABILITY_CAPMASK_LIB LIBCAPABILITY_CAPMASK_BIN
#define _PATH_LIB "/lib"
#define _PATH_USR_LIB "/usr/lib"
#define LIBC_SO "libc.so.7"
-#define LIBBZ2_SO "libbz2.so.3"
#define LIBCAPABILITY_SO "libcapability.so.1"
+#define LIBSBUF_SO "libsbuf.so.4"
extern char **environ;
@@ -150,11 +149,13 @@
static void
lch_sandbox(int fd_sock, int fd_sandbox, int fd_ldso, int fd_libc,
- int fd_libz, int fd_libbz2, int fd_libcapability, int fd_devnull,
- u_int flags, const char *binname, char *const argv[])
+ int fd_libcapability, int fd_libsbuf, int fd_devnull, u_int flags,
+ struct lc_library *lclp, u_int lcl_count, const char *binname,
+ char *const argv[])
{
- char *env_caplibindex, *env_libcapability_sandbox_api;
- int fd_array[11];
+ int *fd_array, fdcount;
+ struct sbuf *sbufp;
+ u_int i;
if (lc_limitfd(fd_devnull, LIBCAPABILITY_CAPMASK_DEVNULL) < 0)
return;
@@ -164,12 +165,16 @@
return;
if (lc_limitfd(fd_ldso, LIBCAPABILITY_CAPMASK_LDSO) < 0)
return;
- if (lc_limitfd(fd_libc, LIBCAPABILITY_CAPMASK_LIBC) < 0)
+ if (lc_limitfd(fd_libc, LIBCAPABILITY_CAPMASK_LIB) < 0)
+ return;
+ if (lc_limitfd(fd_libcapability, LIBCAPABILITY_CAPMASK_LIB) < 0)
return;
- if (lc_limitfd(fd_libbz2, LIBCAPABILITY_CAPMASK_LIBBZ2) < 0)
+ if (lc_limitfd(fd_libsbuf, LIBCAPABILITY_CAPMASK_LIB) < 0)
return;
- if (lc_limitfd(fd_libcapability,
- LIBCAPABILITY_CAPMASK_LIBCAPABILITY) < 0)
+
+ fdcount = 10 + lcl_count;
+ fd_array = malloc(fdcount * sizeof(int));
+ if (fd_array == NULL)
return;
fd_array[0] = fd_devnull;
@@ -184,37 +189,44 @@
fd_array[4] = fd_sock;
fd_array[5] = fd_ldso;
fd_array[6] = fd_libc;
- fd_array[7] = fd_libz;
- fd_array[8] = fd_libbz2;
- fd_array[9] = fd_libcapability;
- fd_array[10] = fd_devnull;
+ fd_array[7] = fd_libcapability;
+ fd_array[8] = fd_libsbuf;
+ fd_array[9] = fd_devnull;
+ for (i = 0; i < lcl_count; i++) {
+ if (lc_limitfd(lclp->lcl_fd, LIBCAPABILITY_CAPMASK_LIB) < 0)
+ return;
+ fd_array[i + 10] = lclp[i].lcl_fd;
+ }
- if (lch_installfds(11, fd_array) < 0)
+ if (lch_installfds(fdcount, fd_array) < 0)
return;
- /*
- * Pass library list into rtld-elf-cap.
- */
- if (asprintf(&env_caplibindex,
- "%d:%s,%d:%s,%d:%s,%d:%s,%d:%s,%d:%s,%d:%s",
- 3, binname, 5, LD_ELF_CAP_SO, 6, LIBC_SO, 7,
- LIBBZ2_SO, 8, LIBCAPABILITY_SO, 9, _PATH_DEVNULL) == -1)
+ sbufp = sbuf_new_auto();
+ if (sbufp == NULL)
+ return;
+ (void)sbuf_printf(sbufp, "%d:%s,%d:%s,%d:%s,%d:%s,%d:%s,%d:%s",
+ 3, binname, 5, LD_ELF_CAP_SO, 6, LIBC_SO, 7, LIBCAPABILITY_SO,
+ 8, LIBSBUF_SO, 9, _PATH_DEVNULL);
+ for (i = 0; i < lcl_count; i++)
+ (void)sbuf_printf(sbufp, ",%d:%s", i + 10,
+ lclp[i].lcl_libname);
+ sbuf_finish(sbufp);
+ if (sbuf_overflowed(sbufp))
return;
- if (setenv("LD_CAPLIBINDEX", env_caplibindex, 1) == -1)
+ if (setenv("LD_CAPLIBINDEX", sbuf_data(sbufp), 1) == -1)
return;
- free(env_caplibindex);
+ sbuf_delete(sbufp);
- /*
- * Make sure that libcapability in the sandbox knows that its API
- * assumptions hold.
- */
- if (asprintf(&env_libcapability_sandbox_api, "%s:%d",
- LIBCAPABILITY_SANDBOX_API_SOCK, 4) == -1)
+ sbufp = sbuf_new_auto();
+ if (sbufp == NULL)
+ return;
+ (void)sbuf_printf(sbufp, "%s:%d", LIBCAPABILITY_SANDBOX_API_SOCK, 4);
+ sbuf_finish(sbufp);
+ if (sbuf_overflowed(sbufp))
return;
- if (setenv(LIBCAPABILITY_SANDBOX_API_ENV,
- env_libcapability_sandbox_api, 1) == -1)
+ if (setenv(LIBCAPABILITY_SANDBOX_API_ENV, sbuf_data(sbufp), 1) == -1)
return;
- free(env_libcapability_sandbox_api);
+ sbuf_delete(sbufp);
if (cap_enter() < 0)
return;
@@ -223,18 +235,18 @@
}
int
-lch_startfd(int fd_sandbox, const char *binname, char *const argv[],
- u_int flags, struct lc_sandbox **lcspp)
+lch_startfd_libs(int fd_sandbox, const char *binname, char *const argv[],
+ u_int flags, struct lc_library *lclp, u_int lcl_count,
+ struct lc_sandbox **lcspp)
{
struct lc_sandbox *lcsp;
- int fd_devnull, fd_ldso, fd_libc, fd_libcapability, fd_libz;
- int fd_libbz2, fd_procdesc, fd_sockpair[2];
+ int fd_devnull, fd_ldso, fd_libc, fd_libcapability, fd_libsbuf;
+ int fd_procdesc, fd_sockpair[2];
int error, val;
pid_t pid;
- fd_devnull = fd_ldso = fd_libc = fd_libz = fd_libbz2 =
- fd_libcapability = fd_procdesc = fd_sockpair[0] =
- fd_sockpair[1] = -1;
+ fd_devnull = fd_ldso = fd_libc = fd_libcapability = fd_libsbuf =
+ fd_procdesc = fd_sockpair[0] = fd_sockpair[1] = -1;
lcsp = malloc(sizeof(*lcsp));
if (lcsp == NULL)
@@ -246,11 +258,11 @@
goto out_error;
if (ld_caplibindex_lookup(LIBC_SO, &fd_libc) < 0)
goto out_error;
- if (ld_caplibindex_lookup(LIBBZ2_SO, &fd_libbz2) < 0)
- goto out_error;
if (ld_caplibindex_lookup(LIBCAPABILITY_SO,
&fd_libcapability) < 0)
goto out_error;
+ if (ld_caplibindex_lookup(LIBSBUF_SO, &fd_libsbuf) < 0)
+ goto out_error;
if (ld_caplibindex_lookup(_PATH_DEVNULL, &fd_devnull) < 0)
goto out_error;
} else {
@@ -261,8 +273,8 @@
fd_libc = open(_PATH_LIB "/" LIBC_SO, O_RDONLY);
if (fd_libc < 0)
goto out_error;
- fd_libbz2 = open(_PATH_USR_LIB "/" LIBBZ2_SO, O_RDONLY);
- if (fd_libbz2 < 0)
+ fd_libsbuf = open(_PATH_LIB "/" LIBSBUF_SO, O_RDONLY);
+ if (fd_libsbuf < 0)
goto out_error;
fd_libcapability = open(_PATH_USR_LIB "/" LIBCAPABILITY_SO,
O_RDONLY);
@@ -290,15 +302,14 @@
}
if (pid == 0) {
lch_sandbox(fd_sockpair[1], fd_sandbox, fd_ldso, fd_libc,
- fd_libz, fd_libbz2, fd_libcapability, fd_devnull, flags,
- binname, argv);
+ fd_libcapability, fd_libsbuf, fd_devnull, flags, lclp,
+ lcl_count, binname, argv);
exit(-1);
}
#ifndef IN_CAP_MODE
close(fd_devnull);
+ close(fd_libsbuf);
close(fd_libcapability);
- close(fd_libz);
- close(fd_libbz2);
close(fd_libc);
close(fd_ldso);
#endif
@@ -320,12 +331,10 @@
#ifndef IN_CAP_MODE
if (fd_devnull != -1)
close(fd_devnull);
+ if (fd_libsbuf != -1)
+ close(fd_libsbuf);
if (fd_libcapability != -1)
close(fd_libcapability);
- if (fd_libz != -1)
- close(fd_libz);
- if (fd_libbz2 != -1)
- close(fd_libbz2);
if (fd_libc != -1)
close(fd_libc);
if (fd_ldso != -1)
@@ -338,8 +347,17 @@
}
int
-lch_start(const char *sandbox, char *const argv[], u_int flags,
- struct lc_sandbox **lcspp)
+lch_startfd(int fd_sandbox, const char *binname, char *const argv[],
+ u_int flags, struct lc_sandbox **lcspp)
+{
+
+ return (lch_startfd_libs(fd_sandbox, binname, argv, flags, NULL, 0,
+ lcspp));
+}
+
+int
+lch_start_libs(const char *sandbox, char *const argv[], u_int flags,
+ struct lc_library *lclp, u_int lcl_count, struct lc_sandbox **lcspp)
{
char binname[MAXPATHLEN];
int error, fd_sandbox, ret;
@@ -351,13 +369,22 @@
if (fd_sandbox < 0)
return (-1);
- ret = lch_startfd(fd_sandbox, binname, argv, flags, lcspp);
+ ret = lch_startfd_libs(fd_sandbox, binname, argv, flags, lclp,
+ lcl_count, lcspp);
error = errno;
close(fd_sandbox);
errno = error;
return (ret);
}
+int
+lch_start(const char *sandbox, char *const argv[], u_int flags,
+ struct lc_sandbox **lcspp)
+{
+
+ return (lch_start_libs(sandbox, argv, flags, NULL, 0, lcspp));
+}
+
void
lch_stop(struct lc_sandbox *lcsp)
{
More information about the p4-projects
mailing list