MODULE_LICENSE("GPL");
MODULE_VERSION(VERSION_STR);
+struct proc_dir_entry *proc_entry;
static void *mntns_get(struct task_struct *task)
{
(*put_mnt_ns2)(nsproxy->mnt_ns);
nsproxy->mnt_ns = mnt_ns;
- /* Find the root */
- root.mnt = mnt_ns->root;
+ root.mnt = &mnt_ns->root->mnt;
root.dentry = mnt_ns->root->mnt.mnt_root;
path_get(&root);
while(d_mountpoint(root.dentry) && follow_down(&root))
;
- /* Update the pwd and root */
path_get(&root);
path_get(&root);
path_put(&fs->root);
};
void (*free_nsproxy2)(struct nsproxy *ns);
-struct file *(*proc_ns_fget2)(int fd);
struct nsproxy * (*create_new_namespaces)(unsigned long flags,
struct task_struct *tsk, struct fs_struct *new_fs);
void (*switch_task_namespaces2)(struct task_struct *p, struct nsproxy *new);
-static int setns_entry(int fd, int nstype) {
- if (nstype==666) {
+static int setns(struct task_struct *reftask) {
const struct proc_ns_operations *ops;
struct task_struct *tsk = current;
struct nsproxy *new_nsproxy;
- struct proc_inode *ei;
- struct file *file;
int err;
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
- file = (*proc_ns_fget2)(fd);
- if (IS_ERR(file))
- return PTR_ERR(file);
-
err = -EINVAL;
- ei = PROC_I(file->f_dentry->d_inode);
ops = &mntns_operations;
new_nsproxy = (*create_new_namespaces)(0, tsk, tsk->fs);
goto out;
}
- err = ops->install(new_nsproxy, ei->ns);
+ err = ops->install(new_nsproxy, reftask->nsproxy->mnt_ns);
if (err) {
(*free_nsproxy2)(new_nsproxy);
goto out;
}
(*switch_task_namespaces2)(tsk, new_nsproxy);
+ return 0;
out:
- fput(file);
- }
+ return err;
- jprobe_return();
- return 0;
}
-static struct jprobe setns_jprobe = {
- .entry = (kprobe_opcode_t *) setns_entry
-};
-
-static void __exit mntsu_exit(void)
+static void __exit lxcsu_exit(void)
{
- unregister_jprobe(&setns_jprobe);
- printk("Procprotect: Stopped mntsu.\n");
+ remove_proc_entry("lxcsu",NULL);
+ printk("Procprotect: Stopped lxcsu.\n");
+}
+
+int lxcsu_write(struct file *file, const char *buffer, unsigned long count, void *data) {
+ char pidname[PATH_MAX];
+ int pid;
+ struct pid *p;
+ char **s;
+ struct task_struct *task;
+
+ if (current->nsproxy->mnt_ns!=init_task.nsproxy->mnt_ns)
+ return -EPERM;
+
+ if (copy_from_user(pidname, buffer, count)) {
+ return -EFAULT;
+ }
+ if (count && (pidname[count-1]==10 || pidname[count-1]==13)) {
+ pidname[count-1]='\0';
+ }
+ else
+ pidname[count]='\0';
+
+ pid = simple_strtol(pidname,s,10);
+ p = find_vpid(pid);
+ task = get_pid_task(p,PIDTYPE_PID);
+ if (task) {
+ setns(task);
+ }
+ else {
+ printk(KERN_CRIT "Task %d not found",pid);
+ }
+
+ return count;
}
-static int __init mntsu_init(void)
+
+static int __init lxcsu_init(void)
{
int ret=0;
- printk("Mntsu: starting mntsu version %s.\n",
+ printk("Mntsu: starting lxcsu version %s.\n",
VERSION_STR);
- proc_ns_fget2 = kallsyms_lookup_name("proc_ns_fget");
- printk(KERN_CRIT "proc_ns_fget = %x",proc_ns_fget2);
-
+
free_nsproxy2 = kallsyms_lookup_name("free_nsproxy");
printk(KERN_CRIT "free_nsproxy = %x",free_nsproxy2);
put_mnt_ns2 = kallsyms_lookup_name("put_mnt_ns");
printk(KERN_CRIT "Put mnt ns = %x",put_mnt_ns2);
- setns_jprobe.kp.addr =
- (kprobe_opcode_t *) kallsyms_lookup_name("sys_setns");
- if (!setns_jprobe.kp.addr) {
- printk("Couldn't find %s to plant jprobe\n", "do_execve");
- return -1;
- }
-
- if ((ret = register_jprobe(&setns_jprobe)) <0) {
- printk("register_jprobe failed, returned %d\n", ret);
- return -1;
- }
-
+ proc_entry = create_proc_entry("lxcsu", 0644, NULL);
+ proc_entry->write_proc = lxcsu_write;
return ret;
}
-module_init(mntsu_init);
-module_exit(mntsu_exit);
+module_init(lxcsu_init);
+module_exit(lxcsu_exit);