--- linux-2.6.14/drivers/char/random.c 2005-10-28 20:49:21 +0200 +++ linux-2.6.14-vs2.0.1-pre3/drivers/char/random.c 2005-10-29 03:44:35 +0200 @@ -1174,7 +1174,7 @@ static char sysctl_bootid[16]; static int proc_do_uuid(ctl_table *table, int write, struct file *filp, void __user *buffer, size_t *lenp, loff_t *ppos) { - ctl_table fake_table; + ctl_table fake_table = {0}; unsigned char buf[64], tmp_uuid[16], *uuid; uuid = table->data; --- linux-2.6.14/fs/devpts/inode.c 2005-10-28 20:49:44 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/devpts/inode.c 2005-10-29 20:56:53 +0200 @@ -95,7 +125,8 @@ devpts_fill_super(struct super_block *s, inode->i_uid = inode->i_gid = 0; inode->i_mode = S_IFDIR | S_IRUGO | S_IXUGO | S_IWUSR; inode->i_op = &simple_dir_inode_operations; - inode->i_fop = &simple_dir_operations; + inode->i_fop = &devpts_dir_operations; + inode->i_xid = vx_current_xid(); inode->i_nlink = 2; devpts_root = s->s_root = d_alloc_root(inode); --- linux-2.6.14/fs/devpts/inode.c 2005-10-28 20:49:44 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/devpts/inode.c 2005-10-29 20:56:53 +0200 @@ -155,6 +186,8 @@ int devpts_pty_new(struct tty_struct *tt inode->i_gid = config.setgid ? config.gid : current->fsgid; inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME; init_special_inode(inode, S_IFCHR|config.mode, device); + inode->i_op = &devpts_file_inode_operations; + inode->i_xid = vx_current_xid(); inode->u.generic_ip = tty; dentry = get_node(number); --- linux-2.6.14/fs/libfs.c 2005-08-29 22:25:32 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/libfs.c 2005-10-29 04:20:01 +0200 @@ -156,6 +157,8 @@ int dcache_readdir(struct file * filp, v next = list_entry(p, struct dentry, d_child); if (d_unhashed(next) || !next->d_inode) continue; + if (filter && !filter(next)) + continue; spin_unlock(&dcache_lock); if (filldir(dirent, next->d_name.name, next->d_name.len, filp->f_pos, next->d_inode->i_ino, dt_type(next->d_inode)) < 0) --- linux-2.6.14/fs/libfs.c 2005-08-29 22:25:32 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/libfs.c 2005-10-29 04:20:01 +0200 @@ -172,6 +175,18 @@ int dcache_readdir(struct file * filp, v return 0; } +int dcache_readdir(struct file * filp, void * dirent, filldir_t filldir) +{ + return do_dcache_readdir_filter(filp, dirent, filldir, NULL); +} + +int dcache_readdir_filter(struct file * filp, void * dirent, filldir_t filldir, + int (*filter)(struct dentry *)) +{ + return do_dcache_readdir_filter(filp, dirent, filldir, filter); +} + + ssize_t generic_read_dir(struct file *filp, char __user *buf, size_t siz, loff_t *ppos) { return -EISDIR; --- linux-2.6.14/fs/libfs.c 2005-08-29 22:25:32 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/libfs.c 2005-10-29 04:20:01 +0200 @@ -620,6 +635,7 @@ EXPORT_SYMBOL(dcache_dir_close); EXPORT_SYMBOL(dcache_dir_lseek); EXPORT_SYMBOL(dcache_dir_open); EXPORT_SYMBOL(dcache_readdir); +EXPORT_SYMBOL(dcache_readdir_filter); EXPORT_SYMBOL(generic_read_dir); EXPORT_SYMBOL(get_sb_pseudo); EXPORT_SYMBOL(simple_commit_write); --- linux-2.6.14/fs/namei.c 2005-10-28 20:49:44 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/namei.c 2005-10-30 04:29:36 +0100 @@ -691,16 +715,34 @@ static int do_lookup(struct nameidata *n { struct vfsmount *mnt = nd->mnt; struct dentry *dentry = __d_lookup(nd->dentry, name); + struct inode *inode; if (!dentry) goto need_lookup; if (dentry->d_op && dentry->d_op->d_revalidate) goto need_revalidate; + inode = dentry->d_inode; + if (!inode) + goto done; + if (!vx_check(inode->i_xid, VX_WATCH|VX_ADMIN|VX_HOSTID|VX_IDENT)) + goto hidden; + if (inode->i_sb->s_magic == PROC_SUPER_MAGIC) { + struct proc_dir_entry *de = PDE(inode); + + if (de && !vx_hide_check(0, de->vx_flags)) + goto hidden; + } done: path->mnt = mnt; path->dentry = dentry; __follow_mount(path); return 0; +hidden: + vxwprintk(1, "xid=%d did lookup hidden %p[#%d,%lu] »%s«.", + vx_current_xid(), inode, inode->i_xid, inode->i_ino, + vxd_path(dentry, mnt)); + dput(dentry); + return -ENOENT; need_lookup: dentry = real_lookup(nd->dentry, name, nd); --- linux-2.6.14/include/linux/fs.h 2005-10-28 20:49:54 +0200 +++ linux-2.6.14-vs2.0.1-pre3/include/linux/fs.h 2005-10-30 04:30:05 +0100 @@ -1622,6 +1640,7 @@ extern int dcache_dir_open(struct inode extern int dcache_dir_close(struct inode *, struct file *); extern loff_t dcache_dir_lseek(struct file *, loff_t, int); extern int dcache_readdir(struct file *, void *, filldir_t); +extern int dcache_readdir_filter(struct file *, void *, filldir_t, int (*)(struct dentry *)); extern int simple_getattr(struct vfsmount *, struct dentry *, struct kstat *); extern int simple_statfs(struct super_block *, struct kstatfs *); extern int simple_link(struct dentry *, struct inode *, struct dentry *); --- linux-2.6.14/include/linux/ipc.h 2004-08-14 12:54:46 +0200 +++ linux-2.6.14-vs2.0.1-pre3/include/linux/ipc.h 2005-10-29 03:44:35 +0200 @@ -66,6 +66,7 @@ struct kern_ipc_perm mode_t mode; unsigned long seq; void *security; + xid_t xid; }; #endif /* __KERNEL__ */ --- linux-2.6.14/include/linux/sched.h 2005-10-28 20:49:56 +0200 +++ linux-2.6.14-vs2.0.1-pre3/include/linux/sched.h 2005-10-30 04:29:36 +0100 @@ -471,9 +475,10 @@ struct user_struct { /* Hash table maintenance information */ struct list_head uidhash_list; uid_t uid; + xid_t xid; }; -extern struct user_struct *find_user(uid_t); +extern struct user_struct *find_user(xid_t, uid_t); extern struct user_struct root_user; #define INIT_USER (&root_user) --- linux-2.6.14/ipc/msg.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/msg.c 2005-10-29 17:19:34 +0200 @@ -99,6 +99,7 @@ static int newque (key_t key, int msgflg msq->q_perm.mode = (msgflg & S_IRWXUGO); msq->q_perm.key = key; + msq->q_perm.xid = vx_current_xid(); msq->q_perm.security = NULL; retval = security_msg_queue_alloc(msq); --- linux-2.6.14/ipc/msg.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/msg.c 2005-10-29 17:19:34 +0200 @@ -814,6 +815,9 @@ static int sysvipc_msg_proc_show(struct { struct msg_queue *msq = it; + if (!vx_check(msq->q_perm.xid, VX_IDENT)) + return 0; + return seq_printf(s, "%10d %10d %4o %10lu %10lu %5u %5u %5u %5u %5u %5u %10lu %10lu %10lu\n", msq->q_perm.key, --- linux-2.6.14/ipc/sem.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/sem.c 2005-10-29 17:19:57 +0200 @@ -178,6 +178,7 @@ static int newary (key_t key, int nsems, sma->sem_perm.mode = (semflg & S_IRWXUGO); sma->sem_perm.key = key; + sma->sem_perm.xid = vx_current_xid(); sma->sem_perm.security = NULL; retval = security_sem_alloc(sma); --- linux-2.6.14/ipc/sem.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/sem.c 2005-10-29 17:19:57 +0200 @@ -1334,6 +1335,9 @@ static int sysvipc_sem_proc_show(struct { struct sem_array *sma = it; + if (!vx_check(sma->sem_perm.xid, VX_IDENT)) + return 0; + return seq_printf(s, "%10d %10d %4o %10lu %5u %5u %5u %5u %10lu %10lu\n", sma->sem_perm.key, --- linux-2.6.14/ipc/shm.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/shm.c 2005-10-30 04:29:36 +0100 @@ -878,6 +889,9 @@ static int sysvipc_shm_proc_show(struct #define SMALL_STRING "%10d %10d %4o %10u %5u %5u %5d %5u %5u %5u %5u %10lu %10lu %10lu\n" #define BIG_STRING "%10d %10d %4o %21u %5u %5u %5d %5u %5u %5u %5u %10lu %10lu %10lu\n" + if (!vx_check(shp->shm_perm.xid, VX_IDENT)) + return 0; + if (sizeof(size_t) <= sizeof(int)) format = SMALL_STRING; else --- linux-2.6.14/ipc/util.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/util.c 2005-10-29 03:44:35 +0200 @@ -153,7 +153,9 @@ int ipc_findkey(struct ipc_ids* ids, key */ for (id = 0; id <= max_id; id++) { p = ids->entries->p[id]; - if(p==NULL) + if (p==NULL) + continue; + if (!vx_check(p->xid, VX_IDENT)) continue; if (key == p->key) return id; --- linux-2.6.14/ipc/util.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/util.c 2005-10-29 03:44:35 +0200 @@ -466,6 +468,8 @@ int ipcperms (struct kern_ipc_perm *ipcp { /* flag will most probably be 0 or S_...UGO from */ int requested_mode, granted_mode; + if (!vx_check(ipcp->xid, VX_ADMIN|VX_IDENT)) /* maybe just VX_IDENT? */ + return -1; requested_mode = (flag >> 6) | (flag >> 3) | flag; granted_mode = ipcp->mode; if (current->euid == ipcp->cuid || current->euid == ipcp->uid) --- linux-2.6.14/kernel/fork.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/fork.c 2005-10-30 04:29:36 +0100 @@ -102,6 +105,8 @@ static kmem_cache_t *mm_cachep; void free_task(struct task_struct *tsk) { free_thread_info(tsk->thread_info); + clr_vx_info(&tsk->vx_info); + clr_nx_info(&tsk->nx_info); free_task_struct(tsk); } EXPORT_SYMBOL(free_task); --- linux-2.6.14/kernel/fork.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/fork.c 2005-10-30 04:29:36 +0100 @@ -880,6 +891,8 @@ static task_t *copy_process(unsigned lon { int retval; struct task_struct *p = NULL; + struct vx_info *vxi; + struct nx_info *nxi; if ((clone_flags & (CLONE_NEWNS|CLONE_FS)) == (CLONE_NEWNS|CLONE_FS)) return ERR_PTR(-EINVAL); --- linux-2.6.14/kernel/sys.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/sys.c 2005-10-29 04:06:52 +0200 @@ -283,7 +288,8 @@ asmlinkage long sys_setpriority(int whic if (!who) who = current->uid; else - if ((who != current->uid) && !(user = find_user(who))) + if ((who != current->uid) && + !(user = find_user(vx_current_xid(), who))) goto out_unlock; /* No processes for this user */ do_each_thread(g, p) --- linux-2.6.14/kernel/sys.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/sys.c 2005-10-29 04:06:52 +0200 @@ -341,7 +347,8 @@ asmlinkage long sys_getpriority(int whic if (!who) who = current->uid; else - if ((who != current->uid) && !(user = find_user(who))) + if ((who != current->uid) && + !(user = find_user(vx_current_xid(), who))) goto out_unlock; /* No processes for this user */ do_each_thread(g, p) --- linux-2.6.14/kernel/sys.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/sys.c 2005-10-29 04:06:52 +0200 @@ -669,7 +680,7 @@ static int set_user(uid_t new_ruid, int { struct user_struct *new_user; - new_user = alloc_uid(new_ruid); + new_user = alloc_uid(vx_current_xid(), new_ruid); if (!new_user) return -EAGAIN; --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -22,8 +22,8 @@ #define UIDHASH_BITS (CONFIG_BASE_SMALL ? 3 : 8) #define UIDHASH_SZ (1 << UIDHASH_BITS) #define UIDHASH_MASK (UIDHASH_SZ - 1) -#define __uidhashfn(uid) (((uid >> UIDHASH_BITS) + uid) & UIDHASH_MASK) -#define uidhashentry(uid) (uidhash_table + __uidhashfn((uid))) +#define __uidhashfn(xid,uid) ((((uid) >> UIDHASH_BITS) + ((uid)^(xid))) & UIDHASH_MASK) +#define uidhashentry(xid,uid) (uidhash_table + __uidhashfn((xid),(uid))) static kmem_cache_t *uid_cachep; static struct list_head uidhash_table[UIDHASH_SZ]; --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -55,7 +55,7 @@ static inline void uid_hash_remove(struc list_del(&up->uidhash_list); } -static inline struct user_struct *uid_hash_find(uid_t uid, struct list_head *hashent) +static inline struct user_struct *uid_hash_find(xid_t xid, uid_t uid, struct list_head *hashent) { struct list_head *up; --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -64,7 +64,7 @@ static inline struct user_struct *uid_ha user = list_entry(up, struct user_struct, uidhash_list); - if(user->uid == uid) { + if(user->uid == uid && user->xid == xid) { atomic_inc(&user->__count); return user; } --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -79,12 +79,12 @@ static inline struct user_struct *uid_ha * * If the user_struct could not be found, return NULL. */ -struct user_struct *find_user(uid_t uid) +struct user_struct *find_user(xid_t xid, uid_t uid) { struct user_struct *ret; spin_lock(&uidhash_lock); - ret = uid_hash_find(uid, uidhashentry(uid)); + ret = uid_hash_find(xid, uid, uidhashentry(xid, uid)); spin_unlock(&uidhash_lock); return ret; } --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -100,13 +100,13 @@ void free_uid(struct user_struct *up) } } -struct user_struct * alloc_uid(uid_t uid) +struct user_struct * alloc_uid(xid_t xid, uid_t uid) { - struct list_head *hashent = uidhashentry(uid); + struct list_head *hashent = uidhashentry(xid, uid); struct user_struct *up; spin_lock(&uidhash_lock); - up = uid_hash_find(uid, hashent); + up = uid_hash_find(xid, uid, hashent); spin_unlock(&uidhash_lock); if (!up) { --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -116,6 +116,7 @@ struct user_struct * alloc_uid(uid_t uid if (!new) return NULL; new->uid = uid; + new->xid = xid; atomic_set(&new->__count, 1); atomic_set(&new->processes, 0); atomic_set(&new->files, 0); --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -138,7 +139,7 @@ struct user_struct * alloc_uid(uid_t uid * on adding the same user already.. */ spin_lock(&uidhash_lock); - up = uid_hash_find(uid, hashent); + up = uid_hash_find(xid, uid, hashent); if (up) { key_put(new->uid_keyring); key_put(new->session_keyring); --- linux-2.6.14/kernel/user.c 2005-08-29 22:25:43 +0200 +++ linux-2.6.14-vs2.0.1-pre3/kernel/user.c 2005-10-29 03:44:35 +0200 @@ -184,7 +185,7 @@ static int __init uid_cache_init(void) /* Insert the root user immediately (init already runs as root) */ spin_lock(&uidhash_lock); - uid_hash_insert(&root_user, uidhashentry(0)); + uid_hash_insert(&root_user, uidhashentry(0,0)); spin_unlock(&uidhash_lock); return 0; --- linux-2.6.14/fs/ioprio.c 2005-08-29 22:25:31 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/ioprio.c 2005-10-29 04:06:52 +0200 @@ -93,7 +94,7 @@ asmlinkage long sys_ioprio_set(int which if (!who) user = current->user; else - user = find_user(who); + user = find_user(who, vx_current_xid()); if (!user) break; --- linux-2.6.14/fs/ioprio.c 2005-08-29 22:25:31 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/ioprio.c 2005-10-29 04:06:52 +0200 @@ -147,7 +148,7 @@ asmlinkage long sys_ioprio_get(int which if (!who) user = current->user; else - user = find_user(who); + user = find_user(who, vx_current_xid()); if (!user) break; --- linux-2.6.14/fs/locks.c 2005-10-28 20:49:44 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/locks.c 2005-10-29 04:43:34 +0200 @@ -2075,6 +2110,10 @@ int get_locks_status(char *buffer, char list_for_each(tmp, &file_lock_list) { struct list_head *btmp; struct file_lock *fl = list_entry(tmp, struct file_lock, fl_link); + + if (!vx_check(fl->fl_xid, VX_IDENT|VX_WATCH)) + continue; + lock_get_status(q, fl, ++i, ""); move_lock_status(&q, &pos, offset); --- linux-2.6.14/fs/libfs.c 2005-08-29 22:25:32 +0200 +++ linux-2.6.14-vs2.0.1-pre3/fs/libfs.c 2005-10-29 04:20:01 +0200 @@ -122,7 +122,8 @@ static inline unsigned char dt_type(stru * both impossible due to the lock on directory. */ -int dcache_readdir(struct file * filp, void * dirent, filldir_t filldir) +static inline int do_dcache_readdir_filter(struct file * filp, + void * dirent, filldir_t filldir, int (*filter)(struct dentry *dentry)) { struct dentry *dentry = filp->f_dentry; struct dentry *cursor = filp->private_data; --- linux-2.6.14/include/linux/fs.h 2005-10-28 20:49:54 +0200 +++ linux-2.6.14-vs2.0.1-pre3/include/linux/fs.h 2005-10-30 04:30:05 +0100 @@ -665,6 +682,7 @@ struct file_lock { unsigned char fl_type; loff_t fl_start; loff_t fl_end; + xid_t fl_xid; struct fasync_struct * fl_fasync; /* for lease break notifications */ unsigned long fl_break_time; /* for nonblocking lease breaks */ --- linux-2.6.14/ipc/shm.c 2005-10-28 20:49:57 +0200 +++ linux-2.6.14-vs2.0.1-pre3/ipc/shm.c 2005-10-30 04:29:36 +0100 @@ -125,6 +131,7 @@ static void shm_destroy (struct shmid_ke shp->mlock_user); fput (shp->shm_file); security_shm_free(shp); + put_vx_info(vxi); ipc_rcu_putref(shp); }