fail:
        return PTR_ERR(alloc);
 }
+
+int nfs3_proc_set_default_acl(struct inode *dir, struct inode *inode,
+               mode_t mode)
+{
+       struct posix_acl *dfacl, *acl;
+       int error = 0;
+
+       dfacl = nfs3_proc_getacl(dir, ACL_TYPE_DEFAULT);
+       if (IS_ERR(dfacl)) {
+               error = PTR_ERR(dfacl);
+               return (error == -EOPNOTSUPP) ? 0 : error;
+       }
+       if (!dfacl)
+               return 0;
+       acl = posix_acl_clone(dfacl, GFP_KERNEL);
+       error = -ENOMEM;
+       if (!acl)
+               goto out_release_dfacl;
+       error = posix_acl_create_masq(acl, &mode);
+       if (error < 0)
+               goto out_release_acl;
+       error = nfs3_proc_setacls(inode, acl, S_ISDIR(inode->i_mode) ?
+                                                     dfacl : NULL);
+out_release_acl:
+       posix_acl_release(acl);
+out_release_dfacl:
+       posix_acl_release(dfacl);
+       return error;
+}
 
                .fh             = &fhandle,
                .fattr          = &fattr
        };
-       int                     status;
+       mode_t mode = sattr->ia_mode;
+       int status;
 
        dprintk("NFS call  create %s\n", dentry->d_name.name);
        arg.createmode = NFS3_CREATE_UNCHECKED;
                arg.verifier[1] = current->pid;
        }
 
+       sattr->ia_mode &= ~current->fs->umask;
+
 again:
        dir_attr.valid = 0;
        fattr.valid = 0;
                nfs_refresh_inode(dentry->d_inode, &fattr);
                dprintk("NFS reply setattr (post-create): %d\n", status);
        }
+       if (status != 0)
+               goto out;
+       status = nfs3_proc_set_default_acl(dir, dentry->d_inode, mode);
 out:
        dprintk("NFS reply create: %d\n", status);
        return status;
                .fh             = &fhandle,
                .fattr          = &fattr
        };
-       int                     status;
+       int mode = sattr->ia_mode;
+       int status;
 
        dprintk("NFS call  mkdir %s\n", dentry->d_name.name);
        dir_attr.valid = 0;
        fattr.valid = 0;
+
+       sattr->ia_mode &= ~current->fs->umask;
+
        status = rpc_call(NFS_CLIENT(dir), NFS3PROC_MKDIR, &arg, &res, 0);
        nfs_refresh_inode(dir, &dir_attr);
-       if (status == 0)
-               status = nfs_instantiate(dentry, &fhandle, &fattr);
+       if (status != 0)
+               goto out;
+       status = nfs_instantiate(dentry, &fhandle, &fattr);
+       if (status != 0)
+               goto out;
+       status = nfs3_proc_set_default_acl(dir, dentry->d_inode, mode);
+out:
        dprintk("NFS reply mkdir: %d\n", status);
        return status;
 }
                .fh             = &fh,
                .fattr          = &fattr
        };
+       mode_t mode = sattr->ia_mode;
        int status;
 
        switch (sattr->ia_mode & S_IFMT) {
 
        dprintk("NFS call  mknod %s %u:%u\n", dentry->d_name.name,
                        MAJOR(rdev), MINOR(rdev));
+
+       sattr->ia_mode &= ~current->fs->umask;
+
        dir_attr.valid = 0;
        fattr.valid = 0;
        status = rpc_call(NFS_CLIENT(dir), NFS3PROC_MKNOD, &arg, &res, 0);
        nfs_refresh_inode(dir, &dir_attr);
-       if (status == 0)
-               status = nfs_instantiate(dentry, &fh, &fattr);
+       if (status != 0)
+               goto out;
+       status = nfs_instantiate(dentry, &fh, &fattr);
+       if (status != 0)
+               goto out;
+       status = nfs3_proc_set_default_acl(dir, dentry->d_inode, mode);
+out:
        dprintk("NFS reply mknod: %d\n", status);
        return status;
 }
 
 extern struct posix_acl *nfs3_proc_getacl(struct inode *inode, int type);
 extern int nfs3_proc_setacl(struct inode *inode, int type,
                            struct posix_acl *acl);
+extern int nfs3_proc_set_default_acl(struct inode *dir, struct inode *inode,
+               mode_t mode);
+#else
+static inline int nfs3_proc_set_default_acl(struct inode *dir,
+                                           struct inode *inode,
+                                           mode_t mode)
+{
+       return 0;
+}
 #endif /* CONFIG_NFS_V3_ACL */
 
 /*