Re: namespaces (was Re: [Q] don't allow tmpfs to page out)
From: Rutger Nijlunsing
Date: Thu Jul 15 2004 - 16:54:49 EST
On Thu, Jul 15, 2004 at 07:19:09PM +0200, Andries Brouwer wrote:
> On Thu, Jul 15, 2004 at 01:31:08PM +0100, Paul Jakma wrote:
>
> > speaking of which, how does one use namespaces exactly? The kernel
> > appears to maintain mount information per process, but how do you set
> > this up?
> >
> > neither 'man mount/namespace' nor 'appropos namespace' show up
> > anything.
>
> Try "man 2 clone" and look for CLONE_NEWNS.
>
> Somewhere else I wrote
>
> Since 2.4.19/2.5.2, the clone() system call, a generalization of
> Unix fork() and BSD vfork(), may have the CLONE_NEWNS flag, that
> says that all mount information must be copied. Afterwards, mount,
> chroot, pivotroot and similar namespace changing calls done by this
> new process do influence this process and its children, but not other
> processes. In particular, the virtual file /proc/mounts that lists the
> mounted filesystems, is now a symlink to /proc/self/mounts - different
> processes may live in entirely different file hierarchies.
>
> Andries
Or your page at
http://www.win.tue.nl/~aeb/linux/lk/lk-6.html
...which contains a working utility (section 6.3.3).
Attached an adopted version. Call like 'newnamespace /bin/bash' to
start bash in a new namespace.
--
Rutger Nijlunsing ---------------------------- rutger ed tux tmfweb nl
never attribute to a conspiracy which can be explained by incompetence
----------------------------------------------------------------------/* newnamespace.c */
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <signal.h>
#include <sched.h>
#include <sys/types.h>
#include <sys/wait.h>
typedef struct {
char *path;
char **argv;
} FuncInfo;
int childfn(void *p) {
FuncInfo *fi = (FuncInfo *)p;
/* setenv("PS1", "@@ ", 1); */
execv(fi->path, fi->argv);
perror("execl");
fprintf(stderr, "Cannot exec '%s'\n", fi->path);
exit(1);
}
static char *default_path = "/bin/ash";
static char *default_argv[] = {"ash", NULL};
int main(int argc, char *argv[]) {
char buf[10000];
pid_t pid, p;
FuncInfo fi;
if (argc == 1) {
/* No arguments given */
fi.path = default_path;
fi.argv = default_argv;
} else {
int i;
argc--; argv++;
fi.path = *argv;
fi.argv = (char **)malloc(sizeof(char *) * (argc + 1));
for (i = 0; i < argc; i++) {
fi.argv[i] = argv[i];
}
fi.argv[argc] = NULL;
}
pid = clone(childfn, buf + 5000, CLONE_NEWNS | SIGCHLD, &fi);
if ((int) pid == -1) {
perror("clone");
exit(1);
}
p = waitpid(pid, NULL, 0);
if ((int) p == -1) {
perror("waitpid");
exit(1);
}
exit(0);
}