+Sandbox setrlimit(2) jail, new option "--no-rlimit".
authorshort <>
Sat, 13 Sep 2003 18:50:54 +0000 (18:50 +0000)
committershort <>
Sat, 13 Sep 2003 18:50:54 +0000 (18:50 +0000)
Cosmetic: Fixed missing trailing '\n' in chrooted '/etc/passwd'.

src/client/sandbox-server/main.c

index 51430a8..ac5b22a 100644 (file)
@@ -40,6 +40,7 @@
 #include <pwd.h>
 #include <fcntl.h>
 #include <sys/file.h>
+#include <sys/resource.h>
 
 
 /* CONFIG: */
@@ -61,6 +62,7 @@ GQuark r=0;
 static gchar *optarg_setuid=CAPTIVE_SANDBOX_SETUID;
 static gchar *optarg_setgid=CAPTIVE_SANDBOX_SETGID;
 static gchar *optarg_chroot=CAPTIVE_SANDBOX_CHROOT;
+static gint   optarg_no_rlimit=0;
 
 static const struct poptOption popt_table[]={
 #define SANDBOX_SERVER_POPT(longname,argInfoP,argP,descripP,argDescripP) \
@@ -74,9 +76,14 @@ static const struct poptOption popt_table[]={
                        argDescrip: (argDescripP), \
                }
 
-               SANDBOX_SERVER_POPT("setuid"  ,POPT_ARG_STRING,&optarg_setuid,N_("Username or UID to become; \"-\" for disable"),N_("UID")),
-               SANDBOX_SERVER_POPT("setgid"  ,POPT_ARG_STRING,&optarg_setgid,N_("Groupname or GID to become; \"-\" for disable"),N_("GID")),
-               SANDBOX_SERVER_POPT("chroot"  ,POPT_ARG_STRING,&optarg_chroot,N_("Pathname to directory for chroot(2); \"-\" for disable"),N_("directory")),
+               SANDBOX_SERVER_POPT("setuid"   ,POPT_ARG_STRING,&optarg_setuid,
+                               N_("Username or UID to become; \"-\" for disable"),N_("UID")),
+               SANDBOX_SERVER_POPT("setgid"   ,POPT_ARG_STRING,&optarg_setgid,
+                               N_("Groupname or GID to become; \"-\" for disable"),N_("GID")),
+               SANDBOX_SERVER_POPT("chroot"   ,POPT_ARG_STRING,&optarg_chroot,
+                               N_("Pathname to directory for chroot(2); \"-\" for disable"),N_("directory")),
+               SANDBOX_SERVER_POPT("no-rlimit",POPT_ARG_NONE  ,&optarg_no_rlimit,
+                               N_("Disable setrlimit(2) restrictions"),NULL),
 
 #undef SANDBOX_SERVER_POPT
                POPT_AUTOHELP
@@ -273,6 +280,19 @@ int dirfd;
                fatal("Failed to chmod(\"%s\",0%o): %m",dir,0711);
 }
 
+static void sandbox_server_rlimit(int resource,const gchar *resource_string,rlim_t rlim_max)
+{
+struct rlimit rlim;
+
+       rlim.rlim_cur=rlim.rlim_max=rlim_max;
+       if (setrlimit(resource,&rlim))
+               fatal("setrlimit(%s,%d): %m",resource_string,(int)rlim_max);
+       if (getrlimit(resource,&rlim))
+               fatal("getrlimit(%s,%d): %m",resource_string,(int)rlim_max);
+       if (rlim.rlim_cur!=rlim_max || rlim.rlim_max!=rlim_max)
+               fatal("Unsuccessful setrlimit(%s)",resource_string);
+}
+
 static const gchar *chrooted_orbit_dir;
 
 static void chroot_setup(gboolean fragile)
@@ -408,13 +428,25 @@ gint gi;
 FILE *f;
                        if (!(f=fopen("/etc/passwd","w")))
                                fatal("Failed to fopen(\"%s\",\"w\"): %m","/etc/passwd");
-                       if (0>fprintf(f,"%s:*:%d:%d:%s:%s:/bin/false",want_uid_name,(int)want_uid,(int)want_gid,want_uid_name,optarg_chroot))
+                       if (0>fprintf(f,"%s:*:%d:%d:%s:%s:/bin/false\n",want_uid_name,(int)want_uid,(int)want_gid,want_uid_name,optarg_chroot))
                                fatal("Failed to fprintf(\"%s\"): %m","/etc/passwd");
                        if (fclose(f))
                                fatal("Failed to fclose(\"%s\"): %m","/etc/passwd");
                        }
                }
 
+       if (fragile || !optarg_no_rlimit) {
+#define SANDBOX_SERVER_RLIMIT(what,how) sandbox_server_rlimit((what),G_STRINGIFY(what),(how))
+               SANDBOX_SERVER_RLIMIT(RLIMIT_NPROC,0);
+               SANDBOX_SERVER_RLIMIT(RLIMIT_MEMLOCK,0);
+               SANDBOX_SERVER_RLIMIT(RLIMIT_CORE,0);
+               SANDBOX_SERVER_RLIMIT(RLIMIT_FSIZE,0);
+               SANDBOX_SERVER_RLIMIT(RLIMIT_NOFILE,6); /* >=6 */
+               /* FIXME: Why flock(dirfd,...) in chrooted_createdir() succeeds?: */
+               SANDBOX_SERVER_RLIMIT(RLIMIT_LOCKS,0);
+#undef SANDBOX_SERVER_RLIMIT
+               }
+
        if (fragile) {
 gid_t gid_list[2];
 int gid_list_size,i;