Set umask correctly for nfsd kernel threads (bug #721) Without acls, when creating files the umask is applied directly in the vfs. ACLs require that the umask is applied at the file system level, depending on whether or not the containing directory has a default acl. The daemonize() function makes kernel threads share their fs_struct structure with the init process. Among other things, fs_struct contains the umask, so all kernel threads share their umask with init. The kernel nfsd needs to create files with a umask of 0. Init's umask cannot simply be changed to 0 --- this would have side effects on init, and init would have side effects on nfsd. So this patch recreates a fs_struct structure for nfsd kernel threads, and sets its umask to 0. Andreas Gruenbacher , SuSE Labs Index: linux-2.5.74-mm2/fs/nfsd/nfssvc.c =================================================================== --- linux-2.5.74-mm2.orig/fs/nfsd/nfssvc.c 2003-07-08 05:38:00.000000000 +0200 +++ linux-2.5.74-mm2/fs/nfsd/nfssvc.c 2003-07-08 05:52:13.000000000 +0200 @@ -20,6 +20,7 @@ #include #include #include +#include #include #include @@ -168,6 +169,7 @@ static void nfsd(struct svc_rqst *rqstp) { struct svc_serv *serv = rqstp->rq_server; + struct fs_struct *fsp; int err; struct nfsd_list me; sigset_t shutdown_mask, allowed_mask; @@ -178,6 +180,18 @@ nfsd(struct svc_rqst *rqstp) daemonize("nfsd"); current->rlim[RLIMIT_FSIZE].rlim_cur = RLIM_INFINITY; + /* After daemonize() this kernel thread shares current->fs + * with the init process. We need to create files with a + * umask of 0 instead of init's umask. */ + fsp = copy_fs_struct(current->fs); + if (!fsp) { + printk("Unable to start nfsd thread: out of memory\n"); + goto out; + } + exit_fs(current); + current->fs = fsp; + current->fs->umask = 0; + siginitsetinv(&shutdown_mask, SHUTDOWN_SIGS); siginitsetinv(&allowed_mask, ALLOWED_SIGS); @@ -262,6 +276,7 @@ nfsd(struct svc_rqst *rqstp) list_del(&me.list); nfsdstats.th_cnt --; +out: /* Release the thread */ svc_exit_thread(rqstp); Index: linux-2.5.74-mm2/kernel/ksyms.c =================================================================== --- linux-2.5.74-mm2.orig/kernel/ksyms.c 2003-07-08 05:38:00.000000000 +0200 +++ linux-2.5.74-mm2/kernel/ksyms.c 2003-07-08 05:52:30.000000000 +0200 @@ -41,6 +41,7 @@ #include #include #include +#include #include #include #include @@ -76,6 +77,8 @@ EXPORT_SYMBOL(do_mmap_pgoff); EXPORT_SYMBOL(do_munmap); EXPORT_SYMBOL(do_brk); EXPORT_SYMBOL(exit_mm); +EXPORT_SYMBOL_GPL(exit_fs); +EXPORT_SYMBOL_GPL(copy_fs_struct); /* internal kernel memory management */ EXPORT_SYMBOL(__alloc_pages);