]> git.pld-linux.org Git - packages/kernel.git/commitdiff
- updated aufs patch
authorJan Rękorajski <baggins@pld-linux.org>
Sun, 24 Apr 2016 16:34:45 +0000 (18:34 +0200)
committerJan Rękorajski <baggins@pld-linux.org>
Sun, 24 Apr 2016 16:34:45 +0000 (18:34 +0200)
kernel-aufs4.patch

index e9aae06cd3760354d56387a32eadf182a0b2c427..4b7205266b5102832615224efb9c3fe40c066085 100644 (file)
@@ -1,10 +1,10 @@
-aufs4.4 kbuild patch
+aufs4.5 kbuild patch
 
 diff --git a/fs/Kconfig b/fs/Kconfig
-index 6ce72d8..4aa31ea 100644
+index 9adee0d..5e9cfb2 100644
 --- a/fs/Kconfig
 +++ b/fs/Kconfig
-@@ -221,6 +221,7 @@ source "fs/pstore/Kconfig"
+@@ -232,6 +232,7 @@ source "fs/pstore/Kconfig"
  source "fs/sysv/Kconfig"
  source "fs/ufs/Kconfig"
  source "fs/exofs/Kconfig"
@@ -22,7 +22,7 @@ index 79f5225..a7c7f16 100644
  obj-$(CONFIG_EFIVAR_FS)               += efivarfs/
 +obj-$(CONFIG_AUFS_FS)           += aufs/
 diff --git a/include/uapi/linux/Kbuild b/include/uapi/linux/Kbuild
-index c2e5d6c..d736c11 100644
+index ebd10e6..32152e7 100644
 --- a/include/uapi/linux/Kbuild
 +++ b/include/uapi/linux/Kbuild
 @@ -59,6 +59,7 @@ header-y += atmsvc.h
@@ -33,13 +33,13 @@ index c2e5d6c..d736c11 100644
  header-y += auto_fs4.h
  header-y += auto_fs.h
  header-y += auxvec.h
-aufs4.4 base patch
+aufs4.5 base patch
 
 diff --git a/MAINTAINERS b/MAINTAINERS
-index 233f834..c250892 100644
+index 6ee06ea..3147250 100644
 --- a/MAINTAINERS
 +++ b/MAINTAINERS
-@@ -2029,6 +2029,19 @@ F:      include/linux/audit.h
+@@ -2082,6 +2082,19 @@ F:      include/linux/audit.h
  F:    include/uapi/linux/audit.h
  F:    kernel/audit*
  
@@ -60,7 +60,7 @@ index 233f834..c250892 100644
  M:    Miguel Ojeda Sandonis <miguel.ojeda.sandonis@gmail.com>
  W:    http://miguelojeda.es/auxdisplay.htm
 diff --git a/drivers/block/loop.c b/drivers/block/loop.c
-index 423f4ca..abfdd2b 100644
+index 423f4ca..0b816b2 100644
 --- a/drivers/block/loop.c
 +++ b/drivers/block/loop.c
 @@ -706,6 +706,24 @@ static inline int is_loop_device(struct file *file)
@@ -83,16 +83,16 @@ index 423f4ca..abfdd2b 100644
 +      }
 +      return ret;
 +}
-+EXPORT_SYMBOL(loop_backing_file);
++EXPORT_SYMBOL_GPL(loop_backing_file);
 +
  /* loop sysfs attributes */
  
  static ssize_t loop_attr_show(struct device *dev, char *page,
 diff --git a/fs/dcache.c b/fs/dcache.c
-index 5c33aeb..8aa7f26 100644
+index 2398f9f9..318c329 100644
 --- a/fs/dcache.c
 +++ b/fs/dcache.c
-@@ -1167,7 +1167,7 @@ enum d_walk_ret {
+@@ -1156,7 +1156,7 @@ enum d_walk_ret {
   *
   * The @enter() and @finish() callbacks are called with d_lock held.
   */
@@ -101,11 +101,33 @@ index 5c33aeb..8aa7f26 100644
                   enum d_walk_ret (*enter)(void *, struct dentry *),
                   void (*finish)(void *))
  {
+diff --git a/fs/fcntl.c b/fs/fcntl.c
+index 350a2c8..6f42279 100644
+--- a/fs/fcntl.c
++++ b/fs/fcntl.c
+@@ -29,7 +29,7 @@
+ #define SETFL_MASK (O_APPEND | O_NONBLOCK | O_NDELAY | O_DIRECT | O_NOATIME)
+-static int setfl(int fd, struct file * filp, unsigned long arg)
++int setfl(int fd, struct file * filp, unsigned long arg)
+ {
+       struct inode * inode = file_inode(filp);
+       int error = 0;
+@@ -60,6 +60,8 @@ static int setfl(int fd, struct file * filp, unsigned long arg)
+       if (filp->f_op->check_flags)
+               error = filp->f_op->check_flags(arg);
++      if (!error && filp->f_op->setfl)
++              error = filp->f_op->setfl(filp, arg);
+       if (error)
+               return error;
 diff --git a/fs/read_write.c b/fs/read_write.c
-index 819ef3f..fd0414e 100644
+index dadf24e..c8b5b7a 100644
 --- a/fs/read_write.c
 +++ b/fs/read_write.c
-@@ -494,6 +494,28 @@ ssize_t __vfs_write(struct file *file, const char __user *p, size_t count,
+@@ -534,6 +534,28 @@ ssize_t __vfs_write(struct file *file, const char __user *p, size_t count,
  }
  EXPORT_SYMBOL(__vfs_write);
  
@@ -135,10 +157,10 @@ index 819ef3f..fd0414e 100644
  {
        mm_segment_t old_fs;
 diff --git a/fs/splice.c b/fs/splice.c
-index 4cf700d..30a091d 100644
+index 82bc0d6..93aee51 100644
 --- a/fs/splice.c
 +++ b/fs/splice.c
-@@ -1110,8 +1110,8 @@ EXPORT_SYMBOL(generic_splice_sendpage);
+@@ -1108,8 +1108,8 @@ EXPORT_SYMBOL(generic_splice_sendpage);
  /*
   * Attempt to initiate a splice from pipe to file.
   */
@@ -149,7 +171,7 @@ index 4cf700d..30a091d 100644
  {
        ssize_t (*splice_write)(struct pipe_inode_info *, struct file *,
                                loff_t *, size_t, unsigned int);
-@@ -1127,9 +1127,9 @@ static long do_splice_from(struct pipe_inode_info *pipe, struct file *out,
+@@ -1125,9 +1125,9 @@ static long do_splice_from(struct pipe_inode_info *pipe, struct file *out,
  /*
   * Attempt to initiate a splice from a file to a pipe.
   */
@@ -175,10 +197,26 @@ index f87d308..9a290b3 100644
  static inline void fput_light(struct file *file, int fput_needed)
  {
 diff --git a/include/linux/fs.h b/include/linux/fs.h
-index 3aa5142..8d48506 100644
+index ae68100..99fc2bd 100644
 --- a/include/linux/fs.h
 +++ b/include/linux/fs.h
-@@ -1672,6 +1672,12 @@ ssize_t rw_copy_check_uvector(int type, const struct iovec __user * uvector,
+@@ -1260,6 +1260,7 @@ extern void fasync_free(struct fasync_struct *);
+ /* can be called from interrupts */
+ extern void kill_fasync(struct fasync_struct **, int, int);
++extern int setfl(int fd, struct file * filp, unsigned long arg);
+ extern void __f_setown(struct file *filp, struct pid *, enum pid_type, int force);
+ extern void f_setown(struct file *filp, unsigned long arg, int force);
+ extern void f_delown(struct file *filp);
+@@ -1646,6 +1647,7 @@ struct file_operations {
+       ssize_t (*sendpage) (struct file *, struct page *, int, size_t, loff_t *, int);
+       unsigned long (*get_unmapped_area)(struct file *, unsigned long, unsigned long, unsigned long, unsigned long);
+       int (*check_flags)(int);
++      int (*setfl)(struct file *, unsigned long);
+       int (*flock) (struct file *, int, struct file_lock *);
+       ssize_t (*splice_write)(struct pipe_inode_info *, struct file *, loff_t *, size_t, unsigned int);
+       ssize_t (*splice_read)(struct file *, loff_t *, struct pipe_inode_info *, size_t, unsigned int);
+@@ -1704,6 +1706,12 @@ ssize_t rw_copy_check_uvector(int type, const struct iovec __user * uvector,
                              struct iovec *fast_pointer,
                              struct iovec **ret_pointer);
  
@@ -206,13 +244,13 @@ index da2751d..2e0fca6 100644
 +                       struct pipe_inode_info *pipe, size_t len,
 +                       unsigned int flags);
  #endif
-aufs4.4 mmap patch
+aufs4.5 mmap patch
 
 diff --git a/fs/proc/base.c b/fs/proc/base.c
-index 4bd5d31..aa41f2a 100644
+index 4f764c2..229de5e 100644
 --- a/fs/proc/base.c
 +++ b/fs/proc/base.c
-@@ -1921,7 +1921,7 @@ static int proc_map_files_get_link(struct dentry *dentry, struct path *path)
+@@ -1933,7 +1933,7 @@ static int map_files_get_link(struct dentry *dentry, struct path *path)
        down_read(&mm->mmap_sem);
        vma = find_exact_vma(mm, vm_start, vm_end);
        if (vma && vma->vm_file) {
@@ -238,10 +276,10 @@ index f8595e8..cb8eda0 100644
                ino = inode->i_ino;
        }
 diff --git a/fs/proc/task_mmu.c b/fs/proc/task_mmu.c
-index 187b3b5..e03793e 100644
+index fa95ab2..d440354 100644
 --- a/fs/proc/task_mmu.c
 +++ b/fs/proc/task_mmu.c
-@@ -281,7 +281,10 @@ show_map_vma(struct seq_file *m, struct vm_area_struct *vma, int is_pid)
+@@ -298,7 +298,10 @@ show_map_vma(struct seq_file *m, struct vm_area_struct *vma, int is_pid)
        const char *name = NULL;
  
        if (file) {
@@ -253,7 +291,7 @@ index 187b3b5..e03793e 100644
                dev = inode->i_sb->s_dev;
                ino = inode->i_ino;
                pgoff = ((loff_t)vma->vm_pgoff) << PAGE_SHIFT;
-@@ -1505,7 +1508,7 @@ static int show_numa_map(struct seq_file *m, void *v, int is_pid)
+@@ -1576,7 +1579,7 @@ static int show_numa_map(struct seq_file *m, void *v, int is_pid)
        struct proc_maps_private *proc_priv = &numa_priv->proc_maps;
        struct vm_area_struct *vma = v;
        struct numa_maps *md = &numa_priv->md;
@@ -263,10 +301,10 @@ index 187b3b5..e03793e 100644
        struct mm_walk walk = {
                .hugetlb_entry = gather_hugetlb_stats,
 diff --git a/fs/proc/task_nommu.c b/fs/proc/task_nommu.c
-index e0d64c9..7aa92db 100644
+index faacb0c..17b43be 100644
 --- a/fs/proc/task_nommu.c
 +++ b/fs/proc/task_nommu.c
-@@ -160,7 +160,10 @@ static int nommu_vma_show(struct seq_file *m, struct vm_area_struct *vma,
+@@ -163,7 +163,10 @@ static int nommu_vma_show(struct seq_file *m, struct vm_area_struct *vma,
        file = vma->vm_file;
  
        if (file) {
@@ -279,10 +317,10 @@ index e0d64c9..7aa92db 100644
                ino = inode->i_ino;
                pgoff = (loff_t)vma->vm_pgoff << PAGE_SHIFT;
 diff --git a/include/linux/mm.h b/include/linux/mm.h
-index 00bad77..cc616b0 100644
+index 516e149..ddd5454 100644
 --- a/include/linux/mm.h
 +++ b/include/linux/mm.h
-@@ -1183,6 +1183,28 @@ static inline int fixup_user_fault(struct task_struct *tsk,
+@@ -1217,6 +1217,28 @@ static inline int fixup_user_fault(struct task_struct *tsk,
  }
  #endif
  
@@ -312,10 +350,10 @@ index 00bad77..cc616b0 100644
  extern int access_remote_vm(struct mm_struct *mm, unsigned long addr,
                void *buf, int len, int write);
 diff --git a/include/linux/mm_types.h b/include/linux/mm_types.h
-index f8d1492..c3a3760 100644
+index 624b78b..1be91c5 100644
 --- a/include/linux/mm_types.h
 +++ b/include/linux/mm_types.h
-@@ -272,6 +272,7 @@ struct vm_region {
+@@ -269,6 +269,7 @@ struct vm_region {
        unsigned long   vm_top;         /* region allocated to here */
        unsigned long   vm_pgoff;       /* the offset in vm_file corresponding to vm_start */
        struct file     *vm_file;       /* the backing file or NULL */
@@ -323,7 +361,7 @@ index f8d1492..c3a3760 100644
  
        int             vm_usage;       /* region usage count (access under nommu_region_sem) */
        bool            vm_icache_flushed : 1; /* true if the icache has been flushed for
-@@ -346,6 +347,7 @@ struct vm_area_struct {
+@@ -343,6 +344,7 @@ struct vm_area_struct {
        unsigned long vm_pgoff;         /* Offset (within vm_file) in PAGE_SIZE
                                           units, *not* PAGE_CACHE_SIZE */
        struct file * vm_file;          /* File we map to (can be NULL). */
@@ -332,10 +370,10 @@ index f8d1492..c3a3760 100644
  
  #ifndef CONFIG_MMU
 diff --git a/kernel/fork.c b/kernel/fork.c
-index 1155eac..c001ea4 100644
+index 2e391c7..6c4215c 100644
 --- a/kernel/fork.c
 +++ b/kernel/fork.c
-@@ -465,7 +465,7 @@ static int dup_mmap(struct mm_struct *mm, struct mm_struct *oldmm)
+@@ -464,7 +464,7 @@ static int dup_mmap(struct mm_struct *mm, struct mm_struct *oldmm)
                        struct inode *inode = file_inode(file);
                        struct address_space *mapping = file->f_mapping;
  
@@ -358,10 +396,10 @@ index 2ed4319..e3a53f5 100644
  obj-y += init-mm.o
  
 diff --git a/mm/filemap.c b/mm/filemap.c
-index 1bb0076..8eaece8 100644
+index da7a35d..f800f87 100644
 --- a/mm/filemap.c
 +++ b/mm/filemap.c
-@@ -2128,7 +2128,7 @@ int filemap_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf)
+@@ -2229,7 +2229,7 @@ int filemap_page_mkwrite(struct vm_area_struct *vma, struct vm_fault *vmf)
        int ret = VM_FAULT_LOCKED;
  
        sb_start_pagefault(inode->i_sb);
@@ -371,10 +409,10 @@ index 1bb0076..8eaece8 100644
        if (page->mapping != inode->i_mapping) {
                unlock_page(page);
 diff --git a/mm/memory.c b/mm/memory.c
-index c387430..d434404 100644
+index 8132787..3f7de66 100644
 --- a/mm/memory.c
 +++ b/mm/memory.c
-@@ -2035,7 +2035,7 @@ static inline int wp_page_reuse(struct mm_struct *mm,
+@@ -2042,7 +2042,7 @@ static inline int wp_page_reuse(struct mm_struct *mm,
                }
  
                if (!page_mkwrite)
@@ -384,10 +422,10 @@ index c387430..d434404 100644
  
        return VM_FAULT_WRITE;
 diff --git a/mm/mmap.c b/mm/mmap.c
-index 2ce04a6..f555c0a 100644
+index 76d1ec2..fdd163e 100644
 --- a/mm/mmap.c
 +++ b/mm/mmap.c
-@@ -275,7 +275,7 @@ static struct vm_area_struct *remove_vma(struct vm_area_struct *vma)
+@@ -290,7 +290,7 @@ static struct vm_area_struct *remove_vma(struct vm_area_struct *vma)
        if (vma->vm_ops && vma->vm_ops->close)
                vma->vm_ops->close(vma);
        if (vma->vm_file)
@@ -396,7 +434,7 @@ index 2ce04a6..f555c0a 100644
        mpol_put(vma_policy(vma));
        kmem_cache_free(vm_area_cachep, vma);
        return next;
-@@ -887,7 +887,7 @@ again:                     remove_next = 1 + (end > next->vm_end);
+@@ -909,7 +909,7 @@ again:                     remove_next = 1 + (end > next->vm_end);
        if (remove_next) {
                if (file) {
                        uprobe_munmap(next, next->vm_start, next->vm_end);
@@ -405,7 +443,7 @@ index 2ce04a6..f555c0a 100644
                }
                if (next->anon_vma)
                        anon_vma_merge(vma, next);
-@@ -1681,8 +1681,8 @@ out:
+@@ -1683,8 +1683,8 @@ out:
        return addr;
  
  unmap_and_free_vma:
@@ -415,7 +453,7 @@ index 2ce04a6..f555c0a 100644
  
        /* Undo any partial mapping done by a device driver. */
        unmap_region(mm, vma, prev, vma->vm_start, vma->vm_end);
-@@ -2488,7 +2488,7 @@ static int __split_vma(struct mm_struct *mm, struct vm_area_struct *vma,
+@@ -2479,7 +2479,7 @@ static int __split_vma(struct mm_struct *mm, struct vm_area_struct *vma,
                goto out_free_mpol;
  
        if (new->vm_file)
@@ -424,7 +462,7 @@ index 2ce04a6..f555c0a 100644
  
        if (new->vm_ops && new->vm_ops->open)
                new->vm_ops->open(new);
-@@ -2507,7 +2507,7 @@ static int __split_vma(struct mm_struct *mm, struct vm_area_struct *vma,
+@@ -2498,7 +2498,7 @@ static int __split_vma(struct mm_struct *mm, struct vm_area_struct *vma,
        if (new->vm_ops && new->vm_ops->close)
                new->vm_ops->close(new);
        if (new->vm_file)
@@ -433,7 +471,7 @@ index 2ce04a6..f555c0a 100644
        unlink_anon_vmas(new);
   out_free_mpol:
        mpol_put(vma_policy(new));
-@@ -2649,7 +2649,6 @@ SYSCALL_DEFINE5(remap_file_pages, unsigned long, start, unsigned long, size,
+@@ -2640,7 +2640,6 @@ SYSCALL_DEFINE5(remap_file_pages, unsigned long, start, unsigned long, size,
        struct vm_area_struct *vma;
        unsigned long populate = 0;
        unsigned long ret = -EINVAL;
@@ -441,8 +479,8 @@ index 2ce04a6..f555c0a 100644
  
        pr_warn_once("%s (%d) uses deprecated remap_file_pages() syscall. "
                        "See Documentation/vm/remap_file_pages.txt.\n",
-@@ -2693,10 +2692,10 @@ SYSCALL_DEFINE5(remap_file_pages, unsigned long, start, unsigned long, size,
-               munlock_vma_pages_range(vma, start, start + size);
+@@ -2708,10 +2707,10 @@ SYSCALL_DEFINE5(remap_file_pages, unsigned long, start, unsigned long, size,
+               }
        }
  
 -      file = get_file(vma->vm_file);
@@ -454,7 +492,7 @@ index 2ce04a6..f555c0a 100644
  out:
        up_write(&mm->mmap_sem);
        if (populate)
-@@ -2966,7 +2965,7 @@ struct vm_area_struct *copy_vma(struct vm_area_struct **vmap,
+@@ -2982,7 +2981,7 @@ struct vm_area_struct *copy_vma(struct vm_area_struct **vmap,
                if (anon_vma_clone(new_vma, vma))
                        goto out_free_mempol;
                if (new_vma->vm_file)
@@ -464,7 +502,7 @@ index 2ce04a6..f555c0a 100644
                        new_vma->vm_ops->open(new_vma);
                vma_link(mm, new_vma, prev, rb_link, rb_parent);
 diff --git a/mm/nommu.c b/mm/nommu.c
-index 92be862..29179f7 100644
+index fbf6f0f1..1a4a06d 100644
 --- a/mm/nommu.c
 +++ b/mm/nommu.c
 @@ -671,7 +671,7 @@ static void __put_nommu_region(struct vm_region *region)
@@ -599,41 +637,53 @@ index 0000000..b323b8a
 +              fput(pr);
 +}
 +#endif /* !CONFIG_MMU */
-aufs4.4 standalone patch
+aufs4.5 standalone patch
 
 diff --git a/fs/dcache.c b/fs/dcache.c
-index 8aa7f26..f997345 100644
+index 318c329..72d3cc8 100644
 --- a/fs/dcache.c
 +++ b/fs/dcache.c
-@@ -1272,6 +1272,7 @@ rename_retry:
+@@ -1261,6 +1261,7 @@ rename_retry:
        seq = 1;
        goto again;
  }
-+EXPORT_SYMBOL(d_walk);
++EXPORT_SYMBOL_GPL(d_walk);
  
  /*
   * Search for at least 1 mount point in the dentry's subdirs.
 diff --git a/fs/exec.c b/fs/exec.c
-index b06623a..b9206c5 100644
+index dcd4ac7..09a7818 100644
 --- a/fs/exec.c
 +++ b/fs/exec.c
 @@ -103,6 +103,7 @@ bool path_noexec(const struct path *path)
        return (path->mnt->mnt_flags & MNT_NOEXEC) ||
               (path->mnt->mnt_sb->s_iflags & SB_I_NOEXEC);
  }
-+EXPORT_SYMBOL(path_noexec);
++EXPORT_SYMBOL_GPL(path_noexec);
  
  #ifdef CONFIG_USELIB
  /*
+diff --git a/fs/fcntl.c b/fs/fcntl.c
+index 6f42279..04fd33c 100644
+--- a/fs/fcntl.c
++++ b/fs/fcntl.c
+@@ -82,6 +82,7 @@ int setfl(int fd, struct file * filp, unsigned long arg)
+  out:
+       return error;
+ }
++EXPORT_SYMBOL_GPL(setfl);
+ static void f_modown(struct file *filp, struct pid *pid, enum pid_type type,
+                      int force)
 diff --git a/fs/file_table.c b/fs/file_table.c
-index ad17e05..38e046a 100644
+index ad17e05..ae9f267 100644
 --- a/fs/file_table.c
 +++ b/fs/file_table.c
 @@ -147,6 +147,7 @@ over:
        }
        return ERR_PTR(-ENFILE);
  }
-+EXPORT_SYMBOL(get_empty_filp);
++EXPORT_SYMBOL_GPL(get_empty_filp);
  
  /**
   * alloc_file - allocate and initialize a 'struct file'
@@ -641,7 +691,7 @@ index ad17e05..38e046a 100644
  {
        delayed_fput(NULL);
  }
-+EXPORT_SYMBOL(flush_delayed_fput);
++EXPORT_SYMBOL_GPL(flush_delayed_fput);
  
  static DECLARE_DELAYED_WORK(delayed_fput_work, delayed_fput);
  
@@ -649,7 +699,7 @@ index ad17e05..38e046a 100644
  }
  
  EXPORT_SYMBOL(fput);
-+EXPORT_SYMBOL(__fput_sync);
++EXPORT_SYMBOL_GPL(__fput_sync);
  
  void put_filp(struct file *file)
  {
@@ -657,12 +707,12 @@ index ad17e05..38e046a 100644
                file_free(file);
        }
  }
-+EXPORT_SYMBOL(put_filp);
++EXPORT_SYMBOL_GPL(put_filp);
  
  void __init files_init(void)
  { 
 diff --git a/fs/namespace.c b/fs/namespace.c
-index 0570729..ec560d8 100644
+index 4fb1691..97654d2 100644
 --- a/fs/namespace.c
 +++ b/fs/namespace.c
 @@ -463,6 +463,7 @@ void __mnt_drop_write(struct vfsmount *mnt)
@@ -673,16 +723,16 @@ index 0570729..ec560d8 100644
  
  /**
   * mnt_drop_write - give up write access to a mount
-@@ -1803,6 +1804,7 @@ int iterate_mounts(int (*f)(struct vfsmount *, void *), void *arg,
+@@ -1811,6 +1812,7 @@ int iterate_mounts(int (*f)(struct vfsmount *, void *), void *arg,
        }
        return 0;
  }
-+EXPORT_SYMBOL(iterate_mounts);
++EXPORT_SYMBOL_GPL(iterate_mounts);
  
  static void cleanup_group_ids(struct mount *mnt, struct mount *end)
  {
 diff --git a/fs/notify/group.c b/fs/notify/group.c
-index d16b62c..06ca6bc 100644
+index d16b62c..53e45b6 100644
 --- a/fs/notify/group.c
 +++ b/fs/notify/group.c
 @@ -22,6 +22,7 @@
@@ -697,7 +747,7 @@ index d16b62c..06ca6bc 100644
  {
        atomic_inc(&group->refcnt);
  }
-+EXPORT_SYMBOL(fsnotify_get_group);
++EXPORT_SYMBOL_GPL(fsnotify_get_group);
  
  /*
   * Drop a reference to a group.  Free it if it's through.
@@ -705,7 +755,7 @@ index d16b62c..06ca6bc 100644
        if (atomic_dec_and_test(&group->refcnt))
                fsnotify_final_destroy_group(group);
  }
-+EXPORT_SYMBOL(fsnotify_put_group);
++EXPORT_SYMBOL_GPL(fsnotify_put_group);
  
  /*
   * Create a new fsnotify_group and hold a reference for the group returned.
@@ -713,55 +763,55 @@ index d16b62c..06ca6bc 100644
  
        return group;
  }
-+EXPORT_SYMBOL(fsnotify_alloc_group);
++EXPORT_SYMBOL_GPL(fsnotify_alloc_group);
  
  int fsnotify_fasync(int fd, struct file *file, int on)
  {
 diff --git a/fs/notify/mark.c b/fs/notify/mark.c
-index fc0df44..325b5c6 100644
+index 7115c5d..ac2bd69 100644
 --- a/fs/notify/mark.c
 +++ b/fs/notify/mark.c
-@@ -109,6 +109,7 @@ void fsnotify_put_mark(struct fsnotify_mark *mark)
+@@ -113,6 +113,7 @@ void fsnotify_put_mark(struct fsnotify_mark *mark)
                mark->free_mark(mark);
        }
  }
-+EXPORT_SYMBOL(fsnotify_put_mark);
++EXPORT_SYMBOL_GPL(fsnotify_put_mark);
  
  /* Calculate mask of events for a list of marks */
  u32 fsnotify_recalc_mask(struct hlist_head *head)
-@@ -208,6 +209,7 @@ void fsnotify_destroy_mark(struct fsnotify_mark *mark,
+@@ -213,6 +214,7 @@ void fsnotify_destroy_mark(struct fsnotify_mark *mark,
        mutex_unlock(&group->mark_mutex);
        fsnotify_free_mark(mark);
  }
-+EXPORT_SYMBOL(fsnotify_destroy_mark);
++EXPORT_SYMBOL_GPL(fsnotify_destroy_mark);
  
  void fsnotify_destroy_marks(struct hlist_head *head, spinlock_t *lock)
  {
-@@ -392,6 +394,7 @@ err:
+@@ -398,6 +400,7 @@ err:
  
        return ret;
  }
-+EXPORT_SYMBOL(fsnotify_add_mark);
++EXPORT_SYMBOL_GPL(fsnotify_add_mark);
  
  int fsnotify_add_mark(struct fsnotify_mark *mark, struct fsnotify_group *group,
                      struct inode *inode, struct vfsmount *mnt, int allow_dups)
-@@ -492,6 +495,7 @@ void fsnotify_init_mark(struct fsnotify_mark *mark,
+@@ -498,6 +501,7 @@ void fsnotify_init_mark(struct fsnotify_mark *mark,
        atomic_set(&mark->refcnt, 1);
        mark->free_mark = free_mark;
  }
-+EXPORT_SYMBOL(fsnotify_init_mark);
++EXPORT_SYMBOL_GPL(fsnotify_init_mark);
  
- static int fsnotify_mark_destroy(void *ignored)
+ static void fsnotify_mark_destroy(struct work_struct *work)
  {
 diff --git a/fs/open.c b/fs/open.c
-index b6f1e96..4ab0d4e 100644
+index 55bdc75..fd1df73 100644
 --- a/fs/open.c
 +++ b/fs/open.c
 @@ -64,6 +64,7 @@ int do_truncate(struct dentry *dentry, loff_t length, unsigned int time_attrs,
-       mutex_unlock(&dentry->d_inode->i_mutex);
+       inode_unlock(dentry->d_inode);
        return ret;
  }
-+EXPORT_SYMBOL(do_truncate);
++EXPORT_SYMBOL_GPL(do_truncate);
  
  long vfs_truncate(struct path *path, loff_t length)
  {
@@ -769,92 +819,92 @@ index b6f1e96..4ab0d4e 100644
        }
        return 0;
  }
-+EXPORT_SYMBOL(open_check_o_direct);
++EXPORT_SYMBOL_GPL(open_check_o_direct);
  
  static int do_dentry_open(struct file *f,
                          struct inode *inode,
 diff --git a/fs/read_write.c b/fs/read_write.c
-index fd0414e..8ace6ec 100644
+index c8b5b7a..9461d12 100644
 --- a/fs/read_write.c
 +++ b/fs/read_write.c
-@@ -504,6 +504,7 @@ vfs_readf_t vfs_readf(struct file *file)
+@@ -544,6 +544,7 @@ vfs_readf_t vfs_readf(struct file *file)
                return new_sync_read;
        return ERR_PTR(-ENOSYS);
  }
-+EXPORT_SYMBOL(vfs_readf);
++EXPORT_SYMBOL_GPL(vfs_readf);
  
  vfs_writef_t vfs_writef(struct file *file)
  {
-@@ -515,6 +516,7 @@ vfs_writef_t vfs_writef(struct file *file)
+@@ -555,6 +556,7 @@ vfs_writef_t vfs_writef(struct file *file)
                return new_sync_write;
        return ERR_PTR(-ENOSYS);
  }
-+EXPORT_SYMBOL(vfs_writef);
++EXPORT_SYMBOL_GPL(vfs_writef);
  
  ssize_t __kernel_write(struct file *file, const char *buf, size_t count, loff_t *pos)
  {
 diff --git a/fs/splice.c b/fs/splice.c
-index 30a091d..c37c311 100644
+index 93aee51..52d2f5b 100644
 --- a/fs/splice.c
 +++ b/fs/splice.c
-@@ -1123,6 +1123,7 @@ long do_splice_from(struct pipe_inode_info *pipe, struct file *out,
+@@ -1121,6 +1121,7 @@ long do_splice_from(struct pipe_inode_info *pipe, struct file *out,
  
        return splice_write(pipe, out, ppos, len, flags);
  }
-+EXPORT_SYMBOL(do_splice_from);
++EXPORT_SYMBOL_GPL(do_splice_from);
  
  /*
   * Attempt to initiate a splice from a file to a pipe.
-@@ -1149,6 +1150,7 @@ long do_splice_to(struct file *in, loff_t *ppos,
+@@ -1147,6 +1148,7 @@ long do_splice_to(struct file *in, loff_t *ppos,
  
        return splice_read(in, ppos, pipe, len, flags);
  }
-+EXPORT_SYMBOL(do_splice_to);
++EXPORT_SYMBOL_GPL(do_splice_to);
  
  /**
   * splice_direct_to_actor - splices data directly between two non-pipes
 diff --git a/fs/xattr.c b/fs/xattr.c
-index 9b932b9..44c457a 100644
+index 4861322..c4bb039 100644
 --- a/fs/xattr.c
 +++ b/fs/xattr.c
 @@ -207,6 +207,7 @@ vfs_getxattr_alloc(struct dentry *dentry, const char *name, char **xattr_value,
        *xattr_value = value;
        return error;
  }
-+EXPORT_SYMBOL(vfs_getxattr_alloc);
++EXPORT_SYMBOL_GPL(vfs_getxattr_alloc);
  
- /* Compare an extended attribute value with the given value */
- int vfs_xattr_cmp(struct dentry *dentry, const char *xattr_name,
+ ssize_t
+ vfs_getxattr(struct dentry *dentry, const char *name, void *value, size_t size)
 diff --git a/kernel/task_work.c b/kernel/task_work.c
-index 53fa971..f80d564 100644
+index 53fa971..bce3211 100644
 --- a/kernel/task_work.c
 +++ b/kernel/task_work.c
 @@ -118,3 +118,4 @@ void task_work_run(void)
                } while (work);
        }
  }
-+EXPORT_SYMBOL(task_work_run);
++EXPORT_SYMBOL_GPL(task_work_run);
 diff --git a/security/commoncap.c b/security/commoncap.c
-index 1832cf7..987ff5f 100644
+index 48071ed..50a1a40 100644
 --- a/security/commoncap.c
 +++ b/security/commoncap.c
-@@ -1053,12 +1053,14 @@ int cap_mmap_addr(unsigned long addr)
+@@ -1058,12 +1058,14 @@ int cap_mmap_addr(unsigned long addr)
        }
        return ret;
  }
-+EXPORT_SYMBOL(cap_mmap_addr);
++EXPORT_SYMBOL_GPL(cap_mmap_addr);
  
  int cap_mmap_file(struct file *file, unsigned long reqprot,
                  unsigned long prot, unsigned long flags)
  {
        return 0;
  }
-+EXPORT_SYMBOL(cap_mmap_file);
++EXPORT_SYMBOL_GPL(cap_mmap_file);
  
  #ifdef CONFIG_SECURITY
  
 diff --git a/security/device_cgroup.c b/security/device_cgroup.c
-index 03c1652..b00aa76 100644
+index 03c1652..f88c84b 100644
 --- a/security/device_cgroup.c
 +++ b/security/device_cgroup.c
 @@ -7,6 +7,7 @@
@@ -869,19 +919,19 @@ index 03c1652..b00aa76 100644
        return __devcgroup_check_permission(type, imajor(inode), iminor(inode),
                        access);
  }
-+EXPORT_SYMBOL(__devcgroup_inode_permission);
++EXPORT_SYMBOL_GPL(__devcgroup_inode_permission);
  
  int devcgroup_inode_mknod(int mode, dev_t dev)
  {
 diff --git a/security/security.c b/security/security.c
-index 46f405c..54488b0 100644
+index e8ffd92..51fa026 100644
 --- a/security/security.c
 +++ b/security/security.c
 @@ -433,6 +433,7 @@ int security_path_rmdir(struct path *dir, struct dentry *dentry)
                return 0;
        return call_int_hook(path_rmdir, 0, dir, dentry);
  }
-+EXPORT_SYMBOL(security_path_rmdir);
++EXPORT_SYMBOL_GPL(security_path_rmdir);
  
  int security_path_unlink(struct path *dir, struct dentry *dentry)
  {
@@ -889,7 +939,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(path_symlink, 0, dir, dentry, old_name);
  }
-+EXPORT_SYMBOL(security_path_symlink);
++EXPORT_SYMBOL_GPL(security_path_symlink);
  
  int security_path_link(struct dentry *old_dentry, struct path *new_dir,
                       struct dentry *new_dentry)
@@ -897,7 +947,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(path_link, 0, old_dentry, new_dir, new_dentry);
  }
-+EXPORT_SYMBOL(security_path_link);
++EXPORT_SYMBOL_GPL(security_path_link);
  
  int security_path_rename(struct path *old_dir, struct dentry *old_dentry,
                         struct path *new_dir, struct dentry *new_dentry,
@@ -905,7 +955,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(path_truncate, 0, path);
  }
-+EXPORT_SYMBOL(security_path_truncate);
++EXPORT_SYMBOL_GPL(security_path_truncate);
  
  int security_path_chmod(struct path *path, umode_t mode)
  {
@@ -913,7 +963,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(path_chmod, 0, path, mode);
  }
-+EXPORT_SYMBOL(security_path_chmod);
++EXPORT_SYMBOL_GPL(security_path_chmod);
  
  int security_path_chown(struct path *path, kuid_t uid, kgid_t gid)
  {
@@ -921,7 +971,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(path_chown, 0, path, uid, gid);
  }
-+EXPORT_SYMBOL(security_path_chown);
++EXPORT_SYMBOL_GPL(security_path_chown);
  
  int security_path_chroot(struct path *path)
  {
@@ -929,7 +979,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(inode_readlink, 0, dentry);
  }
-+EXPORT_SYMBOL(security_inode_readlink);
++EXPORT_SYMBOL_GPL(security_inode_readlink);
  
  int security_inode_follow_link(struct dentry *dentry, struct inode *inode,
                               bool rcu)
@@ -937,7 +987,7 @@ index 46f405c..54488b0 100644
                return 0;
        return call_int_hook(inode_permission, 0, inode, mask);
  }
-+EXPORT_SYMBOL(security_inode_permission);
++EXPORT_SYMBOL_GPL(security_inode_permission);
  
  int security_inode_setattr(struct dentry *dentry, struct iattr *attr)
  {
@@ -945,7 +995,7 @@ index 46f405c..54488b0 100644
  
        return fsnotify_perm(file, mask);
  }
-+EXPORT_SYMBOL(security_file_permission);
++EXPORT_SYMBOL_GPL(security_file_permission);
  
  int security_file_alloc(struct file *file)
  {
@@ -953,13 +1003,13 @@ index 46f405c..54488b0 100644
                return ret;
        return ima_file_mmap(file, prot);
  }
-+EXPORT_SYMBOL(security_mmap_file);
++EXPORT_SYMBOL_GPL(security_mmap_file);
  
  int security_mmap_addr(unsigned long addr)
  {
 diff -urN /usr/share/empty/Documentation/ABI/testing/debugfs-aufs linux/Documentation/ABI/testing/debugfs-aufs
 --- /usr/share/empty/Documentation/ABI/testing/debugfs-aufs    1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/ABI/testing/debugfs-aufs       2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/ABI/testing/debugfs-aufs       2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,50 @@
 +What:         /debug/aufs/si_<id>/
 +Date:         March 2009
@@ -1013,7 +1063,7 @@ diff -urN /usr/share/empty/Documentation/ABI/testing/debugfs-aufs linux/Document
 +              will be empty. About XINO files, see the aufs manual.
 diff -urN /usr/share/empty/Documentation/ABI/testing/sysfs-aufs linux/Documentation/ABI/testing/sysfs-aufs
 --- /usr/share/empty/Documentation/ABI/testing/sysfs-aufs      1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/ABI/testing/sysfs-aufs 2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/ABI/testing/sysfs-aufs 2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,31 @@
 +What:         /sys/fs/aufs/si_<id>/
 +Date:         March 2009
@@ -1048,7 +1098,7 @@ diff -urN /usr/share/empty/Documentation/ABI/testing/sysfs-aufs linux/Documentat
 +              will be empty. About XINO files, see the aufs manual.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/01intro.txt linux/Documentation/filesystems/aufs/design/01intro.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/01intro.txt 1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/01intro.txt    2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/01intro.txt    2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,170 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -1222,7 +1272,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/01intro.txt lin
 +about it. But currently I have implemented it in kernel space.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/02struct.txt linux/Documentation/filesystems/aufs/design/02struct.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/02struct.txt        1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/02struct.txt   2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/02struct.txt   2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,258 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -1484,7 +1534,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/02struct.txt li
 +For this purpose, use "aumvdown" command in aufs-util.git.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/03atomic_open.txt linux/Documentation/filesystems/aufs/design/03atomic_open.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/03atomic_open.txt   1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/03atomic_open.txt      2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/03atomic_open.txt      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,85 @@
 +
 +# Copyright (C) 2015-2016 Junjiro R. Okajima
@@ -1573,7 +1623,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/03atomic_open.t
 +       be implemented in aufs, but not all I am afraid.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/03lookup.txt linux/Documentation/filesystems/aufs/design/03lookup.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/03lookup.txt        1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/03lookup.txt   2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/03lookup.txt   2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,113 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -1690,7 +1740,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/03lookup.txt li
 +   by over-mounting something (or another method).
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/04branch.txt linux/Documentation/filesystems/aufs/design/04branch.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/04branch.txt        1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/04branch.txt   2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/04branch.txt   2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,74 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -1768,7 +1818,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/04branch.txt li
 +    same named entry on the upper branch.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/05wbr_policy.txt linux/Documentation/filesystems/aufs/design/05wbr_policy.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/05wbr_policy.txt    1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/05wbr_policy.txt       2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/05wbr_policy.txt       2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,64 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -1836,7 +1886,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/05wbr_policy.tx
 +  copyup policy.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/06fhsm.txt linux/Documentation/filesystems/aufs/design/06fhsm.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/06fhsm.txt  1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/06fhsm.txt     2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/06fhsm.txt     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,120 @@
 +
 +# Copyright (C) 2011-2016 Junjiro R. Okajima
@@ -1960,7 +2010,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/06fhsm.txt linu
 +should restore the original file state after an error happens.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/06mmap.txt linux/Documentation/filesystems/aufs/design/06mmap.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/06mmap.txt  1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/06mmap.txt     2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/06mmap.txt     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,72 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -2036,7 +2086,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/06mmap.txt linu
 +I have to give up this "looks-smater" approach.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/06xattr.txt linux/Documentation/filesystems/aufs/design/06xattr.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/06xattr.txt 1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/06xattr.txt    2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/06xattr.txt    2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,96 @@
 +
 +# Copyright (C) 2014-2016 Junjiro R. Okajima
@@ -2136,7 +2186,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/06xattr.txt lin
 +now, aufs implements the branch attributes to ignore the error.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/07export.txt linux/Documentation/filesystems/aufs/design/07export.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/07export.txt        1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/07export.txt   2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/07export.txt   2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,58 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -2198,7 +2248,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/07export.txt li
 +  lookup_one_len(), vfs_getattr(), encode_fh() and others.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/08shwh.txt linux/Documentation/filesystems/aufs/design/08shwh.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/08shwh.txt  1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/08shwh.txt     2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/08shwh.txt     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,52 @@
 +
 +# Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -2254,7 +2304,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/08shwh.txt linu
 +initramfs will use it to replace the old one at the next boot.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/10dynop.txt linux/Documentation/filesystems/aufs/design/10dynop.txt
 --- /usr/share/empty/Documentation/filesystems/aufs/design/10dynop.txt 1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/design/10dynop.txt    2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/design/10dynop.txt    2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,47 @@
 +
 +# Copyright (C) 2010-2016 Junjiro R. Okajima
@@ -2305,7 +2355,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/design/10dynop.txt lin
 +regular files only.
 diff -urN /usr/share/empty/Documentation/filesystems/aufs/README linux/Documentation/filesystems/aufs/README
 --- /usr/share/empty/Documentation/filesystems/aufs/README     1970-01-01 01:00:00.000000000 +0100
-+++ linux/Documentation/filesystems/aufs/README        2016-02-28 11:26:32.569971135 +0100
++++ linux/Documentation/filesystems/aufs/README        2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,391 @@
 +
 +Aufs4 -- advanced multi layered unification filesystem version 4.x
@@ -2700,7 +2750,7 @@ diff -urN /usr/share/empty/Documentation/filesystems/aufs/README linux/Documenta
 +# End: ;
 diff -urN /usr/share/empty/fs/aufs/aufs.h linux/fs/aufs/aufs.h
 --- /usr/share/empty/fs/aufs/aufs.h    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/aufs.h       2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/aufs.h       2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,59 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -2763,7 +2813,7 @@ diff -urN /usr/share/empty/fs/aufs/aufs.h linux/fs/aufs/aufs.h
 +#endif /* __AUFS_H__ */
 diff -urN /usr/share/empty/fs/aufs/branch.c linux/fs/aufs/branch.c
 --- /usr/share/empty/fs/aufs/branch.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/branch.c     2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/branch.c     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,1407 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -3062,7 +3112,7 @@ diff -urN /usr/share/empty/fs/aufs/branch.c linux/fs/aufs/branch.c
 +{
 +      int err, old_perm;
 +      aufs_bindex_t bindex;
-+      struct mutex *h_mtx;
++      struct inode *h_inode;
 +      struct au_wbr *wbr;
 +      struct au_hinode *hdir;
 +      struct dentry *h_dentry;
@@ -3075,15 +3125,15 @@ diff -urN /usr/share/empty/fs/aufs/branch.c linux/fs/aufs/branch.c
 +      old_perm = br->br_perm;
 +      br->br_perm = new_perm;
 +      hdir = NULL;
-+      h_mtx = NULL;
++      h_inode = NULL;
 +      bindex = au_br_index(sb, br->br_id);
 +      if (0 <= bindex) {
 +              hdir = au_hi(d_inode(sb->s_root), bindex);
 +              au_hn_imtx_lock_nested(hdir, AuLsc_I_PARENT);
 +      } else {
 +              h_dentry = au_br_dentry(br);
-+              h_mtx = &d_inode(h_dentry)->i_mutex;
-+              mutex_lock_nested(h_mtx, AuLsc_I_PARENT);
++              h_inode = d_inode(h_dentry);
++              inode_lock_nested(h_inode, AuLsc_I_PARENT);
 +      }
 +      if (!wbr)
 +              err = au_wh_init(br, sb);
@@ -3095,7 +3145,7 @@ diff -urN /usr/share/empty/fs/aufs/branch.c linux/fs/aufs/branch.c
 +      if (hdir)
 +              au_hn_imtx_unlock(hdir);
 +      else
-+              mutex_unlock(h_mtx);
++              inode_unlock(h_inode);
 +      vfsub_mnt_drop_write(au_br_mnt(br));
 +      br->br_perm = old_perm;
 +
@@ -4174,7 +4224,7 @@ diff -urN /usr/share/empty/fs/aufs/branch.c linux/fs/aufs/branch.c
 +}
 diff -urN /usr/share/empty/fs/aufs/branch.h linux/fs/aufs/branch.h
 --- /usr/share/empty/fs/aufs/branch.h  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/branch.h     2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/branch.h     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,279 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -4457,7 +4507,7 @@ diff -urN /usr/share/empty/fs/aufs/branch.h linux/fs/aufs/branch.h
 +#endif /* __AUFS_BRANCH_H__ */
 diff -urN /usr/share/empty/fs/aufs/conf.mk linux/fs/aufs/conf.mk
 --- /usr/share/empty/fs/aufs/conf.mk   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/conf.mk      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/conf.mk      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,38 @@
 +
 +AuConfStr = CONFIG_AUFS_FS=${CONFIG_AUFS_FS}
@@ -4499,7 +4549,7 @@ diff -urN /usr/share/empty/fs/aufs/conf.mk linux/fs/aufs/conf.mk
 +-include ${srctree}/${src}/conf_priv.mk
 diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 --- /usr/share/empty/fs/aufs/cpup.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/cpup.c       2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/cpup.c       2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,1379 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -4741,7 +4791,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +      size_t sz, rbytes, wbytes;
 +      unsigned char all_zero;
 +      char *p, *zp;
-+      struct mutex *h_mtx;
++      struct inode *h_inode;
 +      /* reduce stack usage */
 +      struct iattr *ia;
 +
@@ -4821,12 +4871,12 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +                      ia->ia_size = dst->f_pos;
 +                      ia->ia_valid = ATTR_SIZE | ATTR_FILE;
 +                      ia->ia_file = dst;
-+                      h_mtx = &file_inode(dst)->i_mutex;
-+                      mutex_lock_nested(h_mtx, AuLsc_I_CHILD2);
++                      h_inode = file_inode(dst);
++                      inode_lock_nested(h_inode, AuLsc_I_CHILD2);
 +                      /* no delegation since it is just created */
 +                      err = vfsub_notify_change(&dst->f_path, ia,
 +                                                /*delegated*/NULL);
-+                      mutex_unlock(h_mtx);
++                      inode_unlock(h_inode);
 +              }
 +      }
 +
@@ -4954,7 +5004,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +              cpg->len = l;
 +      if (cpg->len) {
 +              /* try stopping to update while we are referencing */
-+              mutex_lock_nested(&h_src_inode->i_mutex, AuLsc_I_CHILD);
++              inode_lock_nested(h_src_inode, AuLsc_I_CHILD);
 +              au_pin_hdir_unlock(cpg->pin);
 +
 +              h_path.dentry = au_h_dptr(cpg->dentry, cpg->bsrc);
@@ -4963,17 +5013,17 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +              if (!au_test_nfs(h_src_inode->i_sb))
 +                      err = vfs_getattr(&h_path, &h_src_attr->st);
 +              else {
-+                      mutex_unlock(&h_src_inode->i_mutex);
++                      inode_unlock(h_src_inode);
 +                      err = vfs_getattr(&h_path, &h_src_attr->st);
-+                      mutex_lock_nested(&h_src_inode->i_mutex, AuLsc_I_CHILD);
++                      inode_lock_nested(h_src_inode, AuLsc_I_CHILD);
 +              }
 +              if (unlikely(err)) {
-+                      mutex_unlock(&h_src_inode->i_mutex);
++                      inode_unlock(h_src_inode);
 +                      goto out;
 +              }
 +              h_src_attr->valid = 1;
 +              err = au_cp_regular(cpg);
-+              mutex_unlock(&h_src_inode->i_mutex);
++              inode_unlock(h_src_inode);
 +              rerr = au_pin_hdir_relock(cpg->pin);
 +              if (!err && rerr)
 +                      err = rerr;
@@ -5324,7 +5374,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +      if (unlikely(err))
 +              goto out_rev;
 +      dst_inode = d_inode(h_dst);
-+      mutex_lock_nested(&dst_inode->i_mutex, AuLsc_I_CHILD2);
++      inode_lock_nested(dst_inode, AuLsc_I_CHILD2);
 +      /* todo: necessary? */
 +      /* au_pin_hdir_unlock(cpg->pin); */
 +
@@ -5332,7 +5382,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +      if (unlikely(err)) {
 +              /* todo: necessary? */
 +              /* au_pin_hdir_relock(cpg->pin); */ /* ignore an error */
-+              mutex_unlock(&dst_inode->i_mutex);
++              inode_unlock(dst_inode);
 +              goto out_rev;
 +      }
 +
@@ -5342,7 +5392,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +                      if (unlikely(err)) {
 +                              /* ignore an error */
 +                              /* au_pin_hdir_relock(cpg->pin); */
-+                              mutex_unlock(&dst_inode->i_mutex);
++                              inode_unlock(dst_inode);
 +                              goto out_rev;
 +                      }
 +              }
@@ -5354,7 +5404,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +
 +      /* todo: necessary? */
 +      /* err = au_pin_hdir_relock(cpg->pin); */
-+      mutex_unlock(&dst_inode->i_mutex);
++      inode_unlock(dst_inode);
 +      if (unlikely(err))
 +              goto out_rev;
 +
@@ -5728,7 +5778,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +              h_tmpdir = d_inode(h_orph);
 +              au_set_h_iptr(dir, bdst, au_igrab(h_tmpdir), /*flags*/0);
 +
-+              mutex_lock_nested(&h_tmpdir->i_mutex, AuLsc_I_PARENT3);
++              inode_lock_nested(h_tmpdir, AuLsc_I_PARENT3);
 +              /* todo: au_h_open_pre()? */
 +
 +              pin_orig = cpg->pin;
@@ -5752,7 +5802,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +      }
 +
 +      if (h_orph) {
-+              mutex_unlock(&h_tmpdir->i_mutex);
++              inode_unlock(h_tmpdir);
 +              /* todo: au_h_open_post()? */
 +              au_set_h_iptr(dir, bdst, au_igrab(h_dir), /*flags*/0);
 +              au_set_h_dptr(parent, bdst, h_parent);
@@ -5882,7 +5932,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.c linux/fs/aufs/cpup.c
 +}
 diff -urN /usr/share/empty/fs/aufs/cpup.h linux/fs/aufs/cpup.h
 --- /usr/share/empty/fs/aufs/cpup.h    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/cpup.h       2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/cpup.h       2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,94 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -5980,7 +6030,7 @@ diff -urN /usr/share/empty/fs/aufs/cpup.h linux/fs/aufs/cpup.h
 +#endif /* __AUFS_CPUP_H__ */
 diff -urN /usr/share/empty/fs/aufs/dbgaufs.c linux/fs/aufs/dbgaufs.c
 --- /usr/share/empty/fs/aufs/dbgaufs.c 1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dbgaufs.c    2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dbgaufs.c    2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,432 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -6416,7 +6466,7 @@ diff -urN /usr/share/empty/fs/aufs/dbgaufs.c linux/fs/aufs/dbgaufs.c
 +}
 diff -urN /usr/share/empty/fs/aufs/dbgaufs.h linux/fs/aufs/dbgaufs.h
 --- /usr/share/empty/fs/aufs/dbgaufs.h 1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dbgaufs.h    2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dbgaufs.h    2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,48 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -6468,7 +6518,7 @@ diff -urN /usr/share/empty/fs/aufs/dbgaufs.h linux/fs/aufs/dbgaufs.h
 +#endif /* __DBGAUFS_H__ */
 diff -urN /usr/share/empty/fs/aufs/dcsub.c linux/fs/aufs/dcsub.c
 --- /usr/share/empty/fs/aufs/dcsub.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dcsub.c      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dcsub.c      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,224 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -6696,7 +6746,7 @@ diff -urN /usr/share/empty/fs/aufs/dcsub.c linux/fs/aufs/dcsub.c
 +}
 diff -urN /usr/share/empty/fs/aufs/dcsub.h linux/fs/aufs/dcsub.h
 --- /usr/share/empty/fs/aufs/dcsub.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dcsub.h      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dcsub.h      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,136 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -6836,7 +6886,7 @@ diff -urN /usr/share/empty/fs/aufs/dcsub.h linux/fs/aufs/dcsub.h
 +#endif /* __AUFS_DCSUB_H__ */
 diff -urN /usr/share/empty/fs/aufs/debug.c linux/fs/aufs/debug.c
 --- /usr/share/empty/fs/aufs/debug.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/debug.c      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/debug.c      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,438 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -7278,7 +7328,7 @@ diff -urN /usr/share/empty/fs/aufs/debug.c linux/fs/aufs/debug.c
 +}
 diff -urN /usr/share/empty/fs/aufs/debug.h linux/fs/aufs/debug.h
 --- /usr/share/empty/fs/aufs/debug.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/debug.h      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/debug.h      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,225 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -7507,7 +7557,7 @@ diff -urN /usr/share/empty/fs/aufs/debug.h linux/fs/aufs/debug.h
 +#endif /* __AUFS_DEBUG_H__ */
 diff -urN /usr/share/empty/fs/aufs/dentry.c linux/fs/aufs/dentry.c
 --- /usr/share/empty/fs/aufs/dentry.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dentry.c     2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dentry.c     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,1136 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -7612,9 +7662,9 @@ diff -urN /usr/share/empty/fs/aufs/dentry.c linux/fs/aufs/dentry.c
 +          || (d_really_is_positive(dentry) && !d_is_dir(dentry)))
 +              goto out; /* success */
 +
-+      mutex_lock_nested(&h_inode->i_mutex, AuLsc_I_CHILD);
++      inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +      opq = au_diropq_test(h_dentry);
-+      mutex_unlock(&h_inode->i_mutex);
++      inode_unlock(h_inode);
 +      if (opq > 0)
 +              au_set_dbdiropq(dentry, bindex);
 +      else if (unlikely(opq < 0)) {
@@ -7691,10 +7741,10 @@ diff -urN /usr/share/empty/fs/aufs/dentry.c linux/fs/aufs/dentry.c
 +                      continue;
 +
 +              h_dir = d_inode(h_parent);
-+              mutex_lock_nested(&h_dir->i_mutex, AuLsc_I_PARENT);
++              inode_lock_nested(h_dir, AuLsc_I_PARENT);
 +              h_dentry = au_do_lookup(h_parent, dentry, bindex, &whname,
 +                                      &args);
-+              mutex_unlock(&h_dir->i_mutex);
++              inode_unlock(h_dir);
 +              err = PTR_ERR(h_dentry);
 +              if (IS_ERR(h_dentry))
 +                      goto out_parent;
@@ -8647,7 +8697,7 @@ diff -urN /usr/share/empty/fs/aufs/dentry.c linux/fs/aufs/dentry.c
 +};
 diff -urN /usr/share/empty/fs/aufs/dentry.h linux/fs/aufs/dentry.h
 --- /usr/share/empty/fs/aufs/dentry.h  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dentry.h     2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dentry.h     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,234 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -8885,7 +8935,7 @@ diff -urN /usr/share/empty/fs/aufs/dentry.h linux/fs/aufs/dentry.h
 +#endif /* __AUFS_DENTRY_H__ */
 diff -urN /usr/share/empty/fs/aufs/dinfo.c linux/fs/aufs/dinfo.c
 --- /usr/share/empty/fs/aufs/dinfo.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dinfo.c      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dinfo.c      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,550 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -9439,8 +9489,8 @@ diff -urN /usr/share/empty/fs/aufs/dinfo.c linux/fs/aufs/dinfo.c
 +}
 diff -urN /usr/share/empty/fs/aufs/dir.c linux/fs/aufs/dir.c
 --- /usr/share/empty/fs/aufs/dir.c     1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dir.c        2016-02-28 11:26:32.569971135 +0100
-@@ -0,0 +1,758 @@
++++ linux/fs/aufs/dir.c        2016-04-24 18:32:51.390353525 +0200
+@@ -0,0 +1,756 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -9884,13 +9934,11 @@ diff -urN /usr/share/empty/fs/aufs/dir.c linux/fs/aufs/dir.c
 +      struct dentry *dentry;
 +      struct inode *inode;
 +      struct super_block *sb;
-+      struct mutex *mtx;
 +
 +      err = 0;
 +      dentry = file->f_path.dentry;
 +      inode = d_inode(dentry);
-+      mtx = &inode->i_mutex;
-+      mutex_lock(mtx);
++      inode_lock(inode);
 +      sb = dentry->d_sb;
 +      si_noflush_read_lock(sb);
 +      if (file)
@@ -9905,7 +9953,7 @@ diff -urN /usr/share/empty/fs/aufs/dir.c linux/fs/aufs/dir.c
 +              fi_write_unlock(file);
 +
 +      si_read_unlock(sb);
-+      mutex_unlock(mtx);
++      inode_unlock(inode);
 +      return err;
 +}
 +
@@ -10079,9 +10127,9 @@ diff -urN /usr/share/empty/fs/aufs/dir.c linux/fs/aufs/dir.c
 +      h_dentry = au_h_dptr(dentry, arg->bindex);
 +      h_inode = d_inode(h_dentry);
 +      /* todo: i_mode changes anytime? */
-+      mutex_lock_nested(&h_inode->i_mutex, AuLsc_I_CHILD);
++      inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +      err = au_test_h_perm_sio(h_inode, MAY_EXEC | MAY_READ);
-+      mutex_unlock(&h_inode->i_mutex);
++      inode_unlock(h_inode);
 +      if (!err)
 +              err = do_test_empty(dentry, arg);
 +      else {
@@ -10201,7 +10249,7 @@ diff -urN /usr/share/empty/fs/aufs/dir.c linux/fs/aufs/dir.c
 +};
 diff -urN /usr/share/empty/fs/aufs/dir.h linux/fs/aufs/dir.h
 --- /usr/share/empty/fs/aufs/dir.h     1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dir.h        2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dir.h        2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,131 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -10336,7 +10384,7 @@ diff -urN /usr/share/empty/fs/aufs/dir.h linux/fs/aufs/dir.h
 +#endif /* __AUFS_DIR_H__ */
 diff -urN /usr/share/empty/fs/aufs/dynop.c linux/fs/aufs/dynop.c
 --- /usr/share/empty/fs/aufs/dynop.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dynop.c      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dynop.c      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,369 @@
 +/*
 + * Copyright (C) 2010-2016 Junjiro R. Okajima
@@ -10709,7 +10757,7 @@ diff -urN /usr/share/empty/fs/aufs/dynop.c linux/fs/aufs/dynop.c
 +}
 diff -urN /usr/share/empty/fs/aufs/dynop.h linux/fs/aufs/dynop.h
 --- /usr/share/empty/fs/aufs/dynop.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/dynop.h      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/dynop.h      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,74 @@
 +/*
 + * Copyright (C) 2010-2016 Junjiro R. Okajima
@@ -10787,8 +10835,8 @@ diff -urN /usr/share/empty/fs/aufs/dynop.h linux/fs/aufs/dynop.h
 +#endif /* __AUFS_DYNOP_H__ */
 diff -urN /usr/share/empty/fs/aufs/export.c linux/fs/aufs/export.c
 --- /usr/share/empty/fs/aufs/export.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/export.c     2016-02-28 11:26:32.569971135 +0100
-@@ -0,0 +1,832 @@
++++ linux/fs/aufs/export.c     2016-04-24 18:32:51.393686895 +0200
+@@ -0,0 +1,830 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -11197,9 +11245,7 @@ diff -urN /usr/share/empty/fs/aufs/export.c linux/fs/aufs/export.c
 +
 +      /* do not call vfsub_lkup_one() */
 +      dir = d_inode(parent);
-+      mutex_lock(&dir->i_mutex);
-+      dentry = vfsub_lookup_one_len(arg.name, parent, arg.namelen);
-+      mutex_unlock(&dir->i_mutex);
++      dentry = vfsub_lookup_one_len_unlocked(arg.name, parent, arg.namelen);
 +      AuTraceErrPtr(dentry);
 +      if (IS_ERR(dentry))
 +              goto out_name;
@@ -11623,7 +11669,7 @@ diff -urN /usr/share/empty/fs/aufs/export.c linux/fs/aufs/export.c
 +}
 diff -urN /usr/share/empty/fs/aufs/fhsm.c linux/fs/aufs/fhsm.c
 --- /usr/share/empty/fs/aufs/fhsm.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/fhsm.c       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/fhsm.c       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,426 @@
 +/*
 + * Copyright (C) 2011-2016 Junjiro R. Okajima
@@ -12053,7 +12099,7 @@ diff -urN /usr/share/empty/fs/aufs/fhsm.c linux/fs/aufs/fhsm.c
 +}
 diff -urN /usr/share/empty/fs/aufs/file.c linux/fs/aufs/file.c
 --- /usr/share/empty/fs/aufs/file.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/file.c       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/file.c       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,844 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -12901,7 +12947,7 @@ diff -urN /usr/share/empty/fs/aufs/file.c linux/fs/aufs/file.c
 +};
 diff -urN /usr/share/empty/fs/aufs/file.h linux/fs/aufs/file.h
 --- /usr/share/empty/fs/aufs/file.h    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/file.h       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/file.h       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,291 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -13196,7 +13242,7 @@ diff -urN /usr/share/empty/fs/aufs/file.h linux/fs/aufs/file.h
 +#endif /* __AUFS_FILE_H__ */
 diff -urN /usr/share/empty/fs/aufs/finfo.c linux/fs/aufs/finfo.c
 --- /usr/share/empty/fs/aufs/finfo.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/finfo.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/finfo.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,156 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -13356,8 +13402,8 @@ diff -urN /usr/share/empty/fs/aufs/finfo.c linux/fs/aufs/finfo.c
 +}
 diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 --- /usr/share/empty/fs/aufs/f_op.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/f_op.c       2016-02-28 11:26:32.569971135 +0100
-@@ -0,0 +1,748 @@
++++ linux/fs/aufs/f_op.c       2016-04-24 18:32:51.393686895 +0200
+@@ -0,0 +1,770 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -13633,11 +13679,11 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +      struct super_block *sb = inode->i_sb;
 +
 +      while (1) {
-+              mutex_lock(&inode->i_mutex);
++              inode_lock(inode);
 +              err = si_read_lock(sb, AuLock_FLUSH | AuLock_NOPLM);
 +              if (!err)
 +                      break;
-+              mutex_unlock(&inode->i_mutex);
++              inode_unlock(inode);
 +              si_read_lock(sb, AuLock_NOPLMW);
 +              si_read_unlock(sb);
 +      }
@@ -13665,7 +13711,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +
 +out:
 +      si_read_unlock(inode->i_sb);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +      return err;
 +}
 +
@@ -13750,7 +13796,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +
 +out:
 +      si_read_unlock(inode->i_sb);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +      return err;
 +}
 +
@@ -13813,7 +13859,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +
 +out:
 +      si_read_unlock(inode->i_sb);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +      return err;
 +}
 +
@@ -13840,7 +13886,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +
 +out:
 +      si_read_unlock(inode->i_sb);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +      return err;
 +}
 +
@@ -13983,7 +14029,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +
 +out_unlock:
 +      si_read_unlock(inode->i_sb);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +out:
 +      return err;
 +}
@@ -13994,7 +14040,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +{
 +      int err;
 +      struct au_write_pre wpre;
-+      struct inode *inode;
++      struct inode *inode, *h_inode;
 +      struct file *file, *h_file;
 +
 +      err = 0; /* -EBADF; */ /* posix? */
@@ -14013,26 +14059,24 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +      err = -ENOSYS;
 +      h_file = au_hf_top(file);
 +      if (h_file->f_op->aio_fsync) {
-+              struct mutex *h_mtx;
-+
-+              h_mtx = &file_inode(h_file)->i_mutex;
++              h_inode = file_inode(h_file);
 +              if (!is_sync_kiocb(kio)) {
 +                      get_file(h_file);
 +                      fput(file);
 +              }
 +              kio->ki_filp = h_file;
 +              err = h_file->f_op->aio_fsync(kio, datasync);
-+              mutex_lock_nested(h_mtx, AuLsc_I_CHILD);
++              inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +              if (!err)
 +                      vfsub_update_h_iattr(&h_file->f_path, /*did*/NULL);
 +              /*ignore*/
-+              mutex_unlock(h_mtx);
++              inode_unlock(h_inode);
 +      }
 +      au_write_post(inode, h_file, &wpre, /*written*/0);
 +
 +out_unlock:
 +      si_read_unlock(inode->sb);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +out:
 +      return err;
 +}
@@ -14061,6 +14105,29 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +      return err;
 +}
 +
++static int aufs_setfl(struct file *file, unsigned long arg)
++{
++      int err;
++      struct file *h_file;
++      struct super_block *sb;
++
++      sb = file->f_path.dentry->d_sb;
++      si_read_lock(sb, AuLock_FLUSH | AuLock_NOPLMW);
++
++      h_file = au_read_pre(file, /*keep_fi*/0);
++      err = PTR_ERR(h_file);
++      if (IS_ERR(h_file))
++              goto out;
++
++      arg |= vfsub_file_flags(file) & FASYNC; /* stop calling h_file->fasync */
++      err = setfl(/*unused fd*/-1, h_file, arg);
++      fput(h_file); /* instead of au_read_post() */
++
++out:
++      si_read_unlock(sb);
++      return err;
++}
++
 +/* ---------------------------------------------------------------------- */
 +
 +/* no one supports this operation, currently */
@@ -14098,6 +14165,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +      /* .aio_fsync   = aufs_aio_fsync_nondir, */
 +      .fasync         = aufs_fasync,
 +      /* .sendpage    = aufs_sendpage, */
++      .setfl          = aufs_setfl,
 +      .splice_write   = aufs_splice_write,
 +      .splice_read    = aufs_splice_read,
 +#if 0
@@ -14108,7 +14176,7 @@ diff -urN /usr/share/empty/fs/aufs/f_op.c linux/fs/aufs/f_op.c
 +};
 diff -urN /usr/share/empty/fs/aufs/fstype.h linux/fs/aufs/fstype.h
 --- /usr/share/empty/fs/aufs/fstype.h  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/fstype.h     2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/fstype.h     2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,400 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -14512,7 +14580,7 @@ diff -urN /usr/share/empty/fs/aufs/fstype.h linux/fs/aufs/fstype.h
 +#endif /* __AUFS_FSTYPE_H__ */
 diff -urN /usr/share/empty/fs/aufs/hfsnotify.c linux/fs/aufs/hfsnotify.c
 --- /usr/share/empty/fs/aufs/hfsnotify.c       1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/hfsnotify.c  2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/hfsnotify.c  2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,288 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -14804,7 +14872,7 @@ diff -urN /usr/share/empty/fs/aufs/hfsnotify.c linux/fs/aufs/hfsnotify.c
 +};
 diff -urN /usr/share/empty/fs/aufs/hfsplus.c linux/fs/aufs/hfsplus.c
 --- /usr/share/empty/fs/aufs/hfsplus.c 1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/hfsplus.c    2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/hfsplus.c    2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,56 @@
 +/*
 + * Copyright (C) 2010-2016 Junjiro R. Okajima
@@ -14864,7 +14932,7 @@ diff -urN /usr/share/empty/fs/aufs/hfsplus.c linux/fs/aufs/hfsplus.c
 +}
 diff -urN /usr/share/empty/fs/aufs/hnotify.c linux/fs/aufs/hnotify.c
 --- /usr/share/empty/fs/aufs/hnotify.c 1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/hnotify.c    2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/hnotify.c    2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,710 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -14951,7 +15019,7 @@ diff -urN /usr/share/empty/fs/aufs/hnotify.c linux/fs/aufs/hnotify.c
 +              if (!hi)
 +                      continue;
 +
-+              /* mutex_lock_nested(&hi->i_mutex, AuLsc_I_CHILD); */
++              /* inode_lock_nested(hi, AuLsc_I_CHILD); */
 +              iwhdentry = au_hi_wh(inode, bindex);
 +              if (iwhdentry)
 +                      dget(iwhdentry);
@@ -14961,7 +15029,7 @@ diff -urN /usr/share/empty/fs/aufs/hnotify.c linux/fs/aufs/hnotify.c
 +                            flags & ~AuHi_XINO);
 +              iput(hi);
 +              dput(iwhdentry);
-+              /* mutex_unlock(&hi->i_mutex); */
++              /* inode_unlock(hi); */
 +      }
 +}
 +
@@ -15190,11 +15258,11 @@ diff -urN /usr/share/empty/fs/aufs/hnotify.c linux/fs/aufs/hnotify.c
 +      if (au_ftest_hnjob(a->flags, TRYXINO0)
 +          && a->inode
 +          && a->h_inode) {
-+              mutex_lock_nested(&a->h_inode->i_mutex, AuLsc_I_CHILD);
++              inode_lock_nested(a->h_inode, AuLsc_I_CHILD);
 +              if (!a->h_inode->i_nlink
 +                  && !(a->h_inode->i_state & I_LINKABLE))
 +                      hn_xino(a->inode, a->h_inode); /* ignore this error */
-+              mutex_unlock(&a->h_inode->i_mutex);
++              inode_unlock(a->h_inode);
 +      }
 +
 +      /* make the generation obsolete */
@@ -15578,7 +15646,7 @@ diff -urN /usr/share/empty/fs/aufs/hnotify.c linux/fs/aufs/hnotify.c
 +}
 diff -urN /usr/share/empty/fs/aufs/iinfo.c linux/fs/aufs/iinfo.c
 --- /usr/share/empty/fs/aufs/iinfo.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/iinfo.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/iinfo.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,277 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -15859,7 +15927,7 @@ diff -urN /usr/share/empty/fs/aufs/iinfo.c linux/fs/aufs/iinfo.c
 +}
 diff -urN /usr/share/empty/fs/aufs/inode.c linux/fs/aufs/inode.c
 --- /usr/share/empty/fs/aufs/inode.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/inode.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/inode.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,527 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -16390,7 +16458,7 @@ diff -urN /usr/share/empty/fs/aufs/inode.c linux/fs/aufs/inode.c
 +}
 diff -urN /usr/share/empty/fs/aufs/inode.h linux/fs/aufs/inode.h
 --- /usr/share/empty/fs/aufs/inode.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/inode.h      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/inode.h      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,685 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -17058,28 +17126,28 @@ diff -urN /usr/share/empty/fs/aufs/inode.h linux/fs/aufs/inode.h
 +
 +static inline void au_hn_imtx_lock(struct au_hinode *hdir)
 +{
-+      mutex_lock(&hdir->hi_inode->i_mutex);
++      inode_lock(hdir->hi_inode);
 +      au_hn_suspend(hdir);
 +}
 +
 +static inline void au_hn_imtx_lock_nested(struct au_hinode *hdir,
 +                                        unsigned int sc __maybe_unused)
 +{
-+      mutex_lock_nested(&hdir->hi_inode->i_mutex, sc);
++      inode_lock_nested(hdir->hi_inode, sc);
 +      au_hn_suspend(hdir);
 +}
 +
 +static inline void au_hn_imtx_unlock(struct au_hinode *hdir)
 +{
 +      au_hn_resume(hdir);
-+      mutex_unlock(&hdir->hi_inode->i_mutex);
++      inode_unlock(hdir->hi_inode);
 +}
 +
 +#endif /* __KERNEL__ */
 +#endif /* __AUFS_INODE_H__ */
 diff -urN /usr/share/empty/fs/aufs/ioctl.c linux/fs/aufs/ioctl.c
 --- /usr/share/empty/fs/aufs/ioctl.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/ioctl.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/ioctl.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,219 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -17302,7 +17370,7 @@ diff -urN /usr/share/empty/fs/aufs/ioctl.c linux/fs/aufs/ioctl.c
 +#endif
 diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 --- /usr/share/empty/fs/aufs/i_op_add.c        1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/i_op_add.c   2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/i_op_add.c   2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,932 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -17720,7 +17788,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 +      };
 +
 +      /* copy-up may happen */
-+      mutex_lock(&dir->i_mutex);
++      inode_lock(dir);
 +
 +      sb = dir->i_sb;
 +      err = si_read_lock(sb, AuLock_FLUSH | AuLock_NOPLM);
@@ -17817,7 +17885,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 +out_si:
 +      si_read_unlock(sb);
 +out:
-+      mutex_unlock(&dir->i_mutex);
++      inode_unlock(dir);
 +      return err;
 +}
 +
@@ -18136,7 +18204,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 +      unsigned char diropq;
 +      struct path h_path;
 +      struct dentry *wh_dentry, *parent, *opq_dentry;
-+      struct mutex *h_mtx;
++      struct inode *h_inode;
 +      struct super_block *sb;
 +      struct {
 +              struct au_pin pin;
@@ -18179,12 +18247,12 @@ diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 +
 +      /* make the dir opaque */
 +      diropq = 0;
-+      h_mtx = &d_inode(h_path.dentry)->i_mutex;
++      h_inode = d_inode(h_path.dentry);
 +      if (wh_dentry
 +          || au_opt_test(au_mntflags(sb), ALWAYS_DIROPQ)) {
-+              mutex_lock_nested(h_mtx, AuLsc_I_CHILD);
++              inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +              opq_dentry = au_diropq_create(dentry, bindex);
-+              mutex_unlock(h_mtx);
++              inode_unlock(h_inode);
 +              err = PTR_ERR(opq_dentry);
 +              if (IS_ERR(opq_dentry))
 +                      goto out_dir;
@@ -18201,9 +18269,9 @@ diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 +      /* revert */
 +      if (diropq) {
 +              AuLabel(revert opq);
-+              mutex_lock_nested(h_mtx, AuLsc_I_CHILD);
++              inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +              rerr = au_diropq_remove(dentry, bindex);
-+              mutex_unlock(h_mtx);
++              inode_unlock(h_inode);
 +              if (rerr) {
 +                      AuIOErr("%pd reverting diropq failed(%d, %d)\n",
 +                              dentry, err, rerr);
@@ -18238,8 +18306,8 @@ diff -urN /usr/share/empty/fs/aufs/i_op_add.c linux/fs/aufs/i_op_add.c
 +}
 diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 --- /usr/share/empty/fs/aufs/i_op.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/i_op.c       2016-02-28 11:26:32.573304539 +0100
-@@ -0,0 +1,1490 @@
++++ linux/fs/aufs/i_op.c       2016-04-24 18:32:51.393686895 +0200
+@@ -0,0 +1,1419 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -18669,10 +18737,10 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +      if (!err && add_entry && !au_ftest_wrdir(add_entry, TMPFILE)) {
 +              h_parent = au_h_dptr(parent, bcpup);
 +              h_dir = d_inode(h_parent);
-+              mutex_lock_nested(&h_dir->i_mutex, AuLsc_I_PARENT);
++              inode_lock_nested(h_dir, AuLsc_I_PARENT);
 +              err = au_lkup_neg(dentry, bcpup, /*wh*/0);
 +              /* todo: no unlock here */
-+              mutex_unlock(&h_dir->i_mutex);
++              inode_unlock(h_dir);
 +
 +              AuDbg("bcpup %d\n", bcpup);
 +              if (!err) {
@@ -19056,10 +19124,10 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +      sz = -1;
 +      a->h_inode = d_inode(a->h_path.dentry);
 +      if (ia && (ia->ia_valid & ATTR_SIZE)) {
-+              mutex_lock_nested(&a->h_inode->i_mutex, AuLsc_I_CHILD);
++              inode_lock_nested(a->h_inode, AuLsc_I_CHILD);
 +              if (ia->ia_size < i_size_read(a->h_inode))
 +                      sz = ia->ia_size;
-+              mutex_unlock(&a->h_inode->i_mutex);
++              inode_unlock(a->h_inode);
 +      }
 +
 +      hi_wh = NULL;
@@ -19119,7 +19187,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +      }
 +out:
 +      if (!err)
-+              mutex_lock_nested(&a->h_inode->i_mutex, AuLsc_I_CHILD);
++              inode_lock_nested(a->h_inode, AuLsc_I_CHILD);
 +      return err;
 +}
 +
@@ -19203,9 +19271,9 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +              f = NULL;
 +              if (ia->ia_valid & ATTR_FILE)
 +                      f = ia->ia_file;
-+              mutex_unlock(&a->h_inode->i_mutex);
++              inode_unlock(a->h_inode);
 +              err = vfsub_trunc(&a->h_path, ia->ia_size, ia->ia_valid, f);
-+              mutex_lock_nested(&a->h_inode->i_mutex, AuLsc_I_CHILD);
++              inode_lock_nested(a->h_inode, AuLsc_I_CHILD);
 +      } else {
 +              delegated = NULL;
 +              while (1) {
@@ -19228,7 +19296,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +              au_cpup_attr_changeable(inode);
 +
 +out_unlock:
-+      mutex_unlock(&a->h_inode->i_mutex);
++      inode_unlock(a->h_inode);
 +      au_unpin(&a->pin);
 +      if (unlikely(err))
 +              au_update_dbstart(dentry);
@@ -19304,7 +19372,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +      if (unlikely(err))
 +              goto out_di;
 +
-+      mutex_unlock(&a->h_inode->i_mutex);
++      inode_unlock(a->h_inode);
 +      switch (arg->type) {
 +      case AU_XATTR_SET:
 +              err = vfsub_setxattr(h_path.dentry,
@@ -19489,62 +19557,20 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +
 +/* ---------------------------------------------------------------------- */
 +
-+/*
-+ * Assumption:
-+ * - the number of symlinks is not so many.
-+ *
-+ * Structure:
-+ * - sbinfo (instead of iinfo) contains an hlist of struct au_symlink.
-+ *   If iinfo contained the hlist, then it would be rather large waste of memory
-+ *   I am afraid.
-+ * - struct au_symlink contains the necessary info for h_inode follow_link() and
-+ *   put_link().
-+ */
-+
-+struct au_symlink {
-+      union {
-+              struct hlist_node hlist;
-+              struct rcu_head rcu;
-+      };
-+
-+      struct inode *h_inode;
-+      void *h_cookie;
-+};
-+
-+static void au_symlink_add(struct super_block *sb, struct au_symlink *slink,
-+                         struct inode *h_inode, void *cookie)
-+{
-+      struct au_sbinfo *sbinfo;
-+
-+      ihold(h_inode);
-+      slink->h_inode = h_inode;
-+      slink->h_cookie = cookie;
-+      sbinfo = au_sbi(sb);
-+      au_sphl_add(&slink->hlist, &sbinfo->si_symlink);
-+}
-+
-+static void au_symlink_del(struct super_block *sb, struct au_symlink *slink)
-+{
-+      struct au_sbinfo *sbinfo;
-+
-+      /* do not iput() within rcu */
-+      iput(slink->h_inode);
-+      slink->h_inode = NULL;
-+      sbinfo = au_sbi(sb);
-+      au_sphl_del_rcu(&slink->hlist, &sbinfo->si_symlink);
-+      kfree_rcu(slink, rcu);
-+}
-+
-+static const char *aufs_follow_link(struct dentry *dentry, void **cookie)
++static const char *aufs_get_link(struct dentry *dentry, struct inode *inode,
++                               struct delayed_call *done)
 +{
 +      const char *ret;
-+      struct inode *inode, *h_inode;
 +      struct dentry *h_dentry;
-+      struct au_symlink *slink;
++      struct inode *h_inode;
 +      int err;
 +      aufs_bindex_t bindex;
 +
 +      ret = NULL; /* suppress a warning */
++      err = -ECHILD;
++      if (!dentry)
++              goto out;
++
 +      err = aufs_read_lock(dentry, AuLock_IR | AuLock_GEN);
 +      if (unlikely(err))
 +              goto out;
@@ -19557,12 +19583,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +      inode = d_inode(dentry);
 +      bindex = au_ibstart(inode);
 +      h_inode = au_h_iptr(inode, bindex);
-+      if (unlikely(!h_inode->i_op->follow_link))
-+              goto out_unlock;
-+
-+      err = -ENOMEM;
-+      slink = kmalloc(sizeof(*slink), GFP_NOFS);
-+      if (unlikely(!slink))
++      if (unlikely(!h_inode->i_op->get_link))
 +              goto out_unlock;
 +
 +      err = -EBUSY;
@@ -19576,28 +19597,20 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +              h_dentry = d_find_any_alias(h_inode);
 +              if (IS_ERR(h_dentry)) {
 +                      err = PTR_ERR(h_dentry);
-+                      goto out_free;
++                      goto out_unlock;
 +              }
 +      }
 +      if (unlikely(!h_dentry))
-+              goto out_free;
++              goto out_unlock;
 +
 +      err = 0;
-+      AuDbg("%pf\n", h_inode->i_op->follow_link);
++      AuDbg("%pf\n", h_inode->i_op->get_link);
 +      AuDbgDentry(h_dentry);
-+      ret = h_inode->i_op->follow_link(h_dentry, cookie);
++      ret = h_inode->i_op->get_link(h_dentry, h_inode, done);
 +      dput(h_dentry);
++      if (IS_ERR(ret))
++              err = PTR_ERR(ret);
 +
-+      if (!IS_ERR_OR_NULL(ret)) {
-+              au_symlink_add(inode->i_sb, slink, h_inode, *cookie);
-+              *cookie = slink;
-+              AuDbg("slink %p\n", slink);
-+              goto out_unlock; /* success */
-+      }
-+
-+out_free:
-+      slink->h_inode = NULL;
-+      kfree_rcu(slink, rcu);
 +out_unlock:
 +      aufs_read_unlock(dentry, AuLock_IR);
 +out:
@@ -19607,21 +19620,6 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +      return ret;
 +}
 +
-+static void aufs_put_link(struct inode *inode, void *cookie)
-+{
-+      struct au_symlink *slink;
-+      struct inode *h_inode;
-+
-+      slink = cookie;
-+      AuDbg("slink %p\n", slink);
-+      h_inode = slink->h_inode;
-+      AuDbg("%pf\n", h_inode->i_op->put_link);
-+      AuDbgInode(h_inode);
-+      if (h_inode->i_op->put_link)
-+              h_inode->i_op->put_link(h_inode, slink->h_cookie);
-+      au_symlink_del(inode->i_sb, slink);
-+}
-+
 +/* ---------------------------------------------------------------------- */
 +
 +static int aufs_update_time(struct inode *inode, struct timespec *ts, int flags)
@@ -19674,8 +19672,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +#endif
 +
 +              .readlink       = generic_readlink,
-+              .follow_link    = aufs_follow_link,
-+              .put_link       = aufs_put_link,
++              .get_link       = aufs_get_link,
 +
 +              /* .update_time = aufs_update_time */
 +      },
@@ -19732,7 +19729,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op.c linux/fs/aufs/i_op.c
 +};
 diff -urN /usr/share/empty/fs/aufs/i_op_del.c linux/fs/aufs/i_op_del.c
 --- /usr/share/empty/fs/aufs/i_op_del.c        1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/i_op_del.c   2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/i_op_del.c   2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,510 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -20246,7 +20243,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op_del.c linux/fs/aufs/i_op_del.c
 +}
 diff -urN /usr/share/empty/fs/aufs/i_op_ren.c linux/fs/aufs/i_op_ren.c
 --- /usr/share/empty/fs/aufs/i_op_ren.c        1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/i_op_ren.c   2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/i_op_ren.c   2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,1015 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -21026,7 +21023,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op_ren.c linux/fs/aufs/i_op_ren.c
 +static void au_ren_rev_dt(int err, struct au_ren_args *a)
 +{
 +      struct dentry *h_d;
-+      struct mutex *h_mtx;
++      struct inode *h_inode;
 +
 +      au_dtime_revert(a->src_dt + AuPARENT);
 +      if (!au_ftest_ren(a->flags, ISSAMEDIR))
@@ -21034,17 +21031,17 @@ diff -urN /usr/share/empty/fs/aufs/i_op_ren.c linux/fs/aufs/i_op_ren.c
 +
 +      if (au_ftest_ren(a->flags, ISDIR) && err != -EIO) {
 +              h_d = a->src_dt[AuCHILD].dt_h_path.dentry;
-+              h_mtx = &d_inode(h_d)->i_mutex;
-+              mutex_lock_nested(h_mtx, AuLsc_I_CHILD);
++              h_inode = d_inode(h_d);
++              inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +              au_dtime_revert(a->src_dt + AuCHILD);
-+              mutex_unlock(h_mtx);
++              inode_unlock(h_inode);
 +
 +              if (au_ftest_ren(a->flags, DT_DSTDIR)) {
 +                      h_d = a->dst_dt[AuCHILD].dt_h_path.dentry;
-+                      h_mtx = &d_inode(h_d)->i_mutex;
-+                      mutex_lock_nested(h_mtx, AuLsc_I_CHILD);
++                      h_inode = d_inode(h_d);
++                      inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +                      au_dtime_revert(a->dst_dt + AuCHILD);
-+                      mutex_unlock(h_mtx);
++                      inode_unlock(h_inode);
 +              }
 +      }
 +}
@@ -21265,7 +21262,7 @@ diff -urN /usr/share/empty/fs/aufs/i_op_ren.c linux/fs/aufs/i_op_ren.c
 +}
 diff -urN /usr/share/empty/fs/aufs/Kconfig linux/fs/aufs/Kconfig
 --- /usr/share/empty/fs/aufs/Kconfig   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/Kconfig      2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/Kconfig      2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,185 @@
 +config AUFS_FS
 +      tristate "Aufs (Advanced multi layered unification filesystem) support"
@@ -21454,7 +21451,7 @@ diff -urN /usr/share/empty/fs/aufs/Kconfig linux/fs/aufs/Kconfig
 +endif
 diff -urN /usr/share/empty/fs/aufs/loop.c linux/fs/aufs/loop.c
 --- /usr/share/empty/fs/aufs/loop.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/loop.c       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/loop.c       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,146 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -21604,7 +21601,7 @@ diff -urN /usr/share/empty/fs/aufs/loop.c linux/fs/aufs/loop.c
 +}
 diff -urN /usr/share/empty/fs/aufs/loop.h linux/fs/aufs/loop.h
 --- /usr/share/empty/fs/aufs/loop.h    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/loop.h       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/loop.h       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,52 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -21660,7 +21657,7 @@ diff -urN /usr/share/empty/fs/aufs/loop.h linux/fs/aufs/loop.h
 +#endif /* __AUFS_LOOP_H__ */
 diff -urN /usr/share/empty/fs/aufs/magic.mk linux/fs/aufs/magic.mk
 --- /usr/share/empty/fs/aufs/magic.mk  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/magic.mk     2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/magic.mk     2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,30 @@
 +
 +# defined in ${srctree}/fs/fuse/inode.c
@@ -21694,7 +21691,7 @@ diff -urN /usr/share/empty/fs/aufs/magic.mk linux/fs/aufs/magic.mk
 +endif
 diff -urN /usr/share/empty/fs/aufs/Makefile linux/fs/aufs/Makefile
 --- /usr/share/empty/fs/aufs/Makefile  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/Makefile     2016-02-28 11:26:32.569971135 +0100
++++ linux/fs/aufs/Makefile     2016-04-24 18:32:51.390353525 +0200
 @@ -0,0 +1,44 @@
 +
 +include ${src}/magic.mk
@@ -21742,7 +21739,7 @@ diff -urN /usr/share/empty/fs/aufs/Makefile linux/fs/aufs/Makefile
 +aufs-$(CONFIG_AUFS_MAGIC_SYSRQ) += sysrq.o
 diff -urN /usr/share/empty/fs/aufs/module.c linux/fs/aufs/module.c
 --- /usr/share/empty/fs/aufs/module.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/module.c     2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/module.c     2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,221 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -21967,7 +21964,7 @@ diff -urN /usr/share/empty/fs/aufs/module.c linux/fs/aufs/module.c
 +module_exit(aufs_exit);
 diff -urN /usr/share/empty/fs/aufs/module.h linux/fs/aufs/module.h
 --- /usr/share/empty/fs/aufs/module.h  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/module.h     2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/module.h     2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,105 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -22076,7 +22073,7 @@ diff -urN /usr/share/empty/fs/aufs/module.h linux/fs/aufs/module.h
 +#endif /* __AUFS_MODULE_H__ */
 diff -urN /usr/share/empty/fs/aufs/mvdown.c linux/fs/aufs/mvdown.c
 --- /usr/share/empty/fs/aufs/mvdown.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/mvdown.c     2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/mvdown.c     2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,703 @@
 +/*
 + * Copyright (C) 2011-2016 Junjiro R. Okajima
@@ -22738,14 +22735,14 @@ diff -urN /usr/share/empty/fs/aufs/mvdown.c linux/fs/aufs/mvdown.c
 +      dmsg = !!(args->mvdown.flags & AUFS_MVDOWN_DMSG);
 +      args->parent = dget_parent(dentry);
 +      args->dir = d_inode(args->parent);
-+      mutex_lock_nested(&args->dir->i_mutex, I_MUTEX_PARENT);
++      inode_lock_nested(args->dir, I_MUTEX_PARENT);
 +      dput(args->parent);
 +      if (unlikely(args->parent != dentry->d_parent)) {
 +              AU_MVD_PR(dmsg, "parent dir is moved\n");
 +              goto out_dir;
 +      }
 +
-+      mutex_lock_nested(&inode->i_mutex, I_MUTEX_CHILD);
++      inode_lock_nested(inode, I_MUTEX_CHILD);
 +      err = aufs_read_lock(dentry, AuLock_DW | AuLock_FLUSH | AuLock_NOPLMW);
 +      if (unlikely(err))
 +              goto out_inode;
@@ -22769,9 +22766,9 @@ diff -urN /usr/share/empty/fs/aufs/mvdown.c linux/fs/aufs/mvdown.c
 +      di_write_unlock(args->parent);
 +      aufs_read_unlock(dentry, AuLock_DW);
 +out_inode:
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +out_dir:
-+      mutex_unlock(&args->dir->i_mutex);
++      inode_unlock(args->dir);
 +out_free:
 +      e = copy_to_user(uarg, &args->mvdown, sizeof(args->mvdown));
 +      if (unlikely(e))
@@ -22783,7 +22780,7 @@ diff -urN /usr/share/empty/fs/aufs/mvdown.c linux/fs/aufs/mvdown.c
 +}
 diff -urN /usr/share/empty/fs/aufs/opts.c linux/fs/aufs/opts.c
 --- /usr/share/empty/fs/aufs/opts.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/opts.c       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/opts.c       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,1859 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -24372,16 +24369,16 @@ diff -urN /usr/share/empty/fs/aufs/opts.c linux/fs/aufs/opts.c
 +              if (unlikely(!au_br_writable(au_sbr_perm(sb, 0))))
 +                      pr_warn("first branch should be rw\n");
 +              if (unlikely(au_opt_test(sbinfo->si_mntflags, SHWH)))
-+                      pr_warn("shwh should be used with ro\n");
++                      pr_warn_once("shwh should be used with ro\n");
 +      }
 +
 +      if (au_opt_test((sbinfo->si_mntflags | pending), UDBA_HNOTIFY)
 +          && !au_opt_test(sbinfo->si_mntflags, XINO))
-+              pr_warn("udba=*notify requires xino\n");
++              pr_warn_once("udba=*notify requires xino\n");
 +
 +      if (au_opt_test(sbinfo->si_mntflags, DIRPERM1))
-+              pr_warn("dirperm1 breaks the protection"
-+                      " by the permission bits on the lower branch\n");
++              pr_warn_once("dirperm1 breaks the protection"
++                           " by the permission bits on the lower branch\n");
 +
 +      err = 0;
 +      fhsm = 0;
@@ -24646,7 +24643,7 @@ diff -urN /usr/share/empty/fs/aufs/opts.c linux/fs/aufs/opts.c
 +}
 diff -urN /usr/share/empty/fs/aufs/opts.h linux/fs/aufs/opts.h
 --- /usr/share/empty/fs/aufs/opts.h    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/opts.h       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/opts.h       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,211 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -24861,7 +24858,7 @@ diff -urN /usr/share/empty/fs/aufs/opts.h linux/fs/aufs/opts.h
 +#endif /* __AUFS_OPTS_H__ */
 diff -urN /usr/share/empty/fs/aufs/plink.c linux/fs/aufs/plink.c
 --- /usr/share/empty/fs/aufs/plink.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/plink.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/plink.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,528 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -25065,12 +25062,12 @@ diff -urN /usr/share/empty/fs/aufs/plink.c linux/fs/aufs/plink.c
 +                                     struct au_branch *br)
 +{
 +      struct dentry *h_dentry;
-+      struct mutex *h_mtx;
++      struct inode *h_inode;
 +
-+      h_mtx = &d_inode(h_parent)->i_mutex;
-+      mutex_lock_nested(h_mtx, AuLsc_I_CHILD2);
++      h_inode = d_inode(h_parent);
++      inode_lock_nested(h_inode, AuLsc_I_CHILD2);
 +      h_dentry = vfsub_lkup_one(tgtname, h_parent);
-+      mutex_unlock(h_mtx);
++      inode_unlock(h_inode);
 +      return h_dentry;
 +}
 +
@@ -25123,7 +25120,7 @@ diff -urN /usr/share/empty/fs/aufs/plink.c linux/fs/aufs/plink.c
 +      struct inode *h_dir, *delegated;
 +
 +      h_dir = d_inode(h_parent);
-+      mutex_lock_nested(&h_dir->i_mutex, AuLsc_I_CHILD2);
++      inode_lock_nested(h_dir, AuLsc_I_CHILD2);
 +again:
 +      h_path.dentry = vfsub_lkup_one(tgt, h_parent);
 +      err = PTR_ERR(h_path.dentry);
@@ -25159,7 +25156,7 @@ diff -urN /usr/share/empty/fs/aufs/plink.c linux/fs/aufs/plink.c
 +      dput(h_path.dentry);
 +
 +out:
-+      mutex_unlock(&h_dir->i_mutex);
++      inode_unlock(h_dir);
 +      return err;
 +}
 +
@@ -25393,7 +25390,7 @@ diff -urN /usr/share/empty/fs/aufs/plink.c linux/fs/aufs/plink.c
 +}
 diff -urN /usr/share/empty/fs/aufs/poll.c linux/fs/aufs/poll.c
 --- /usr/share/empty/fs/aufs/poll.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/poll.c       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/poll.c       2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,52 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -25449,7 +25446,7 @@ diff -urN /usr/share/empty/fs/aufs/poll.c linux/fs/aufs/poll.c
 +}
 diff -urN /usr/share/empty/fs/aufs/posix_acl.c linux/fs/aufs/posix_acl.c
 --- /usr/share/empty/fs/aufs/posix_acl.c       1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/posix_acl.c  2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/posix_acl.c  2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,98 @@
 +/*
 + * Copyright (C) 2014-2016 Junjiro R. Okajima
@@ -25524,7 +25521,7 @@ diff -urN /usr/share/empty/fs/aufs/posix_acl.c linux/fs/aufs/posix_acl.c
 +              },
 +      };
 +
-+      mutex_lock(&inode->i_mutex);
++      inode_lock(inode);
 +      if (inode->i_ino == AUFS_ROOT_INO)
 +              dentry = dget(inode->i_sb->s_root);
 +      else {
@@ -25546,12 +25543,12 @@ diff -urN /usr/share/empty/fs/aufs/posix_acl.c linux/fs/aufs/posix_acl.c
 +              err = 0;
 +
 +out:
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +      return err;
 +}
 diff -urN /usr/share/empty/fs/aufs/procfs.c linux/fs/aufs/procfs.c
 --- /usr/share/empty/fs/aufs/procfs.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/procfs.c     2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/procfs.c     2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,169 @@
 +/*
 + * Copyright (C) 2010-2016 Junjiro R. Okajima
@@ -25724,8 +25721,8 @@ diff -urN /usr/share/empty/fs/aufs/procfs.c linux/fs/aufs/procfs.c
 +}
 diff -urN /usr/share/empty/fs/aufs/rdu.c linux/fs/aufs/rdu.c
 --- /usr/share/empty/fs/aufs/rdu.c     1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/rdu.c        2016-02-28 11:26:32.573304539 +0100
-@@ -0,0 +1,388 @@
++++ linux/fs/aufs/rdu.c        2016-04-24 18:32:51.393686895 +0200
+@@ -0,0 +1,389 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -25887,8 +25884,9 @@ diff -urN /usr/share/empty/fs/aufs/rdu.c linux/fs/aufs/rdu.c
 +      dentry = file->f_path.dentry;
 +      inode = d_inode(dentry);
 +#if 1
-+      mutex_lock(&inode->i_mutex);
++      inode_lock(inode);
 +#else
++      /* todo: create a new inline func inode_lock_killable() */
 +      err = mutex_lock_killable(&inode->i_mutex);
 +      AuTraceErr(err);
 +      if (unlikely(err))
@@ -25950,7 +25948,7 @@ diff -urN /usr/share/empty/fs/aufs/rdu.c linux/fs/aufs/rdu.c
 +out_si:
 +      si_read_unlock(arg.sb);
 +out_mtx:
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +out:
 +      AuTraceErr(err);
 +      return err;
@@ -26116,7 +26114,7 @@ diff -urN /usr/share/empty/fs/aufs/rdu.c linux/fs/aufs/rdu.c
 +#endif
 diff -urN /usr/share/empty/fs/aufs/rwsem.h linux/fs/aufs/rwsem.h
 --- /usr/share/empty/fs/aufs/rwsem.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/rwsem.h      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/rwsem.h      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,191 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -26311,8 +26309,8 @@ diff -urN /usr/share/empty/fs/aufs/rwsem.h linux/fs/aufs/rwsem.h
 +#endif /* __AUFS_RWSEM_H__ */
 diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 --- /usr/share/empty/fs/aufs/sbinfo.c  1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/sbinfo.c     2016-02-28 11:26:32.573304539 +0100
-@@ -0,0 +1,366 @@
++++ linux/fs/aufs/sbinfo.c     2016-04-24 18:32:51.393686895 +0200
+@@ -0,0 +1,350 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -26350,19 +26348,14 @@ diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 +              AuDebugOn(!hlist_empty(&sbinfo->si_plink[i].head));
 +      AuDebugOn(atomic_read(&sbinfo->si_nowait.nw_len));
 +
-+      AuDebugOn(!hlist_empty(&sbinfo->si_symlink.head));
-+
 +      au_rw_write_lock(&sbinfo->si_rwsem);
 +      au_br_free(sbinfo);
 +      au_rw_write_unlock(&sbinfo->si_rwsem);
 +
-+      AuDebugOn(radix_tree_gang_lookup
-+                (&sbinfo->au_si_pid.tree, (void **)&locked,
-+                 /*first_index*/PID_MAX_DEFAULT - 1,
-+                 /*max_items*/sizeof(locked)/sizeof(*locked)));
-+
 +      kfree(sbinfo->si_branch);
-+      kfree(sbinfo->au_si_pid.bitmap);
++      for (i = 0; i < AU_NPIDMAP; i++)
++              kfree(sbinfo->au_si_pid.pid_bitmap[i]);
++      mutex_destroy(&sbinfo->au_si_pid.pid_mtx);
 +      mutex_destroy(&sbinfo->si_xib_mtx);
 +      AuRwDestroy(&sbinfo->si_rwsem);
 +
@@ -26380,18 +26373,10 @@ diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 +      if (unlikely(!sbinfo))
 +              goto out;
 +
-+      BUILD_BUG_ON(sizeof(unsigned long) !=
-+                   sizeof(*sbinfo->au_si_pid.bitmap));
-+      sbinfo->au_si_pid.bitmap = kcalloc(BITS_TO_LONGS(PID_MAX_DEFAULT),
-+                                      sizeof(*sbinfo->au_si_pid.bitmap),
-+                                      GFP_NOFS);
-+      if (unlikely(!sbinfo->au_si_pid.bitmap))
-+              goto out_sbinfo;
-+
 +      /* will be reallocated separately */
 +      sbinfo->si_branch = kzalloc(sizeof(*sbinfo->si_branch), GFP_NOFS);
 +      if (unlikely(!sbinfo->si_branch))
-+              goto out_pidmap;
++              goto out_sbinfo;
 +
 +      err = sysaufs_si_init(sbinfo);
 +      if (unlikely(err))
@@ -26400,8 +26385,7 @@ diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 +      au_nwt_init(&sbinfo->si_nowait);
 +      au_rw_init_wlock(&sbinfo->si_rwsem);
 +      au_rw_class(&sbinfo->si_rwsem, &aufs_si);
-+      spin_lock_init(&sbinfo->au_si_pid.tree_lock);
-+      INIT_RADIX_TREE(&sbinfo->au_si_pid.tree, GFP_ATOMIC | __GFP_NOFAIL);
++      mutex_init(&sbinfo->au_si_pid.pid_mtx);
 +
 +      atomic_long_set(&sbinfo->si_ninodes, 0);
 +      atomic_long_set(&sbinfo->si_nfiles, 0);
@@ -26418,8 +26402,6 @@ diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 +
 +      sbinfo->si_mntflags = au_opts_plink(AuOpt_Def);
 +
-+      au_sphl_init(&sbinfo->si_symlink);
-+
 +      sbinfo->si_xino_jiffy = jiffies;
 +      sbinfo->si_xino_expire
 +              = msecs_to_jiffies(AUFS_XINO_DEF_SEC * MSEC_PER_SEC);
@@ -26452,8 +26434,6 @@ diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 +
 +out_br:
 +      kfree(sbinfo->si_branch);
-+out_pidmap:
-+      kfree(sbinfo->au_si_pid.bitmap);
 +out_sbinfo:
 +      kfree(sbinfo);
 +out:
@@ -26638,50 +26618,52 @@ diff -urN /usr/share/empty/fs/aufs/sbinfo.c linux/fs/aufs/sbinfo.c
 +
 +/* ---------------------------------------------------------------------- */
 +
-+int si_pid_test_slow(struct super_block *sb)
-+{
-+      void *p;
-+
-+      rcu_read_lock();
-+      p = radix_tree_lookup(&au_sbi(sb)->au_si_pid.tree, current->pid);
-+      rcu_read_unlock();
-+
-+      return (long)!!p;
-+}
-+
-+void si_pid_set_slow(struct super_block *sb)
++static void si_pid_alloc(struct au_si_pid *au_si_pid, int idx)
 +{
-+      int err;
-+      struct au_sbinfo *sbinfo;
++      unsigned long *p;
 +
-+      AuDebugOn(si_pid_test_slow(sb));
++      BUILD_BUG_ON(sizeof(unsigned long) !=
++                   sizeof(*au_si_pid->pid_bitmap));
 +
-+      sbinfo = au_sbi(sb);
-+      err = radix_tree_preload(GFP_NOFS | __GFP_NOFAIL);
-+      AuDebugOn(err);
-+      spin_lock(&sbinfo->au_si_pid.tree_lock);
-+      err = radix_tree_insert(&sbinfo->au_si_pid.tree, current->pid,
-+                              /*any valid ptr*/sb);
-+      spin_unlock(&sbinfo->au_si_pid.tree_lock);
-+      AuDebugOn(err);
-+      radix_tree_preload_end();
++      mutex_lock(&au_si_pid->pid_mtx);
++      p = au_si_pid->pid_bitmap[idx];
++      while (!p) {
++              /*
++               * bad approach.
++               * but keeping 'si_pid_set()' void is more important.
++               */
++              p = kcalloc(BITS_TO_LONGS(AU_PIDSTEP),
++                          sizeof(*au_si_pid->pid_bitmap),
++                          GFP_NOFS);
++              if (p)
++                      break;
++              cond_resched();
++      }
++      au_si_pid->pid_bitmap[idx] = p;
++      mutex_unlock(&au_si_pid->pid_mtx);
 +}
 +
-+void si_pid_clr_slow(struct super_block *sb)
++void si_pid_set(struct super_block *sb)
 +{
-+      void *p;
-+      struct au_sbinfo *sbinfo;
-+
-+      AuDebugOn(!si_pid_test_slow(sb));
-+
-+      sbinfo = au_sbi(sb);
-+      spin_lock(&sbinfo->au_si_pid.tree_lock);
-+      p = radix_tree_delete(&sbinfo->au_si_pid.tree, current->pid);
-+      spin_unlock(&sbinfo->au_si_pid.tree_lock);
++      pid_t bit;
++      int idx;
++      unsigned long *bitmap;
++      struct au_si_pid *au_si_pid;
++
++      si_pid_idx_bit(&idx, &bit);
++      au_si_pid = &au_sbi(sb)->au_si_pid;
++      bitmap = au_si_pid->pid_bitmap[idx];
++      if (!bitmap) {
++              si_pid_alloc(au_si_pid, idx);
++              bitmap = au_si_pid->pid_bitmap[idx];
++      }
++      AuDebugOn(test_bit(bit, bitmap));
++      set_bit(bit, bitmap);
++      /* smp_mb(); */
 +}
 diff -urN /usr/share/empty/fs/aufs/spl.h linux/fs/aufs/spl.h
 --- /usr/share/empty/fs/aufs/spl.h     1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/spl.h        2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/spl.h        2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,111 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -26796,7 +26778,7 @@ diff -urN /usr/share/empty/fs/aufs/spl.h linux/fs/aufs/spl.h
 +#endif /* __AUFS_SPL_H__ */
 diff -urN /usr/share/empty/fs/aufs/super.c linux/fs/aufs/super.c
 --- /usr/share/empty/fs/aufs/super.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/super.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/super.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,1039 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -27604,7 +27586,7 @@ diff -urN /usr/share/empty/fs/aufs/super.c linux/fs/aufs/super.c
 +
 +      sbinfo = au_sbi(sb);
 +      inode = d_inode(root);
-+      mutex_lock(&inode->i_mutex);
++      inode_lock(inode);
 +      err = si_write_lock(sb, AuLock_FLUSH | AuLock_NOPLM);
 +      if (unlikely(err))
 +              goto out_mtx;
@@ -27627,7 +27609,7 @@ diff -urN /usr/share/empty/fs/aufs/super.c linux/fs/aufs/super.c
 +      aufs_write_unlock(root);
 +
 +out_mtx:
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +out_opts:
 +      free_page((unsigned long)opts.opt);
 +out:
@@ -27746,7 +27728,7 @@ diff -urN /usr/share/empty/fs/aufs/super.c linux/fs/aufs/super.c
 +              goto out_root;
 +
 +      /* lock vfs_inode first, then aufs. */
-+      mutex_lock(&inode->i_mutex);
++      inode_lock(inode);
 +      aufs_write_lock(root);
 +      err = au_opts_mount(sb, &opts);
 +      au_opts_free(&opts);
@@ -27758,7 +27740,7 @@ diff -urN /usr/share/empty/fs/aufs/super.c linux/fs/aufs/super.c
 +              au_refresh_iop(inode, /*force_getattr*/0);
 +      }
 +      aufs_write_unlock(root);
-+      mutex_unlock(&inode->i_mutex);
++      inode_unlock(inode);
 +      if (!err)
 +              goto out_opts; /* success */
 +
@@ -27839,8 +27821,8 @@ diff -urN /usr/share/empty/fs/aufs/super.c linux/fs/aufs/super.c
 +};
 diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 --- /usr/share/empty/fs/aufs/super.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/super.h      2016-02-28 11:26:32.573304539 +0100
-@@ -0,0 +1,641 @@
++++ linux/fs/aufs/super.h      2016-04-24 18:32:51.393686895 +0200
+@@ -0,0 +1,632 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -27930,6 +27912,13 @@ diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 +#endif
 +};
 +
++#define AU_PIDSTEP    (int)(BITS_TO_LONGS(PID_MAX_DEFAULT) * BITS_PER_LONG)
++#define AU_NPIDMAP    (int)DIV_ROUND_UP(PID_MAX_LIMIT, AU_PIDSTEP)
++struct au_si_pid {
++      unsigned long   *pid_bitmap[AU_NPIDMAP];
++      struct mutex    pid_mtx;
++};
++
 +struct au_branch;
 +struct au_sbinfo {
 +      /* nowait tasks in the system-wide workqueue */
@@ -27942,11 +27931,7 @@ diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 +      struct au_rwsem         si_rwsem;
 +
 +      /* prevent recursive locking in deleting inode */
-+      struct {
-+              unsigned long           *bitmap;
-+              spinlock_t              tree_lock;
-+              struct radix_tree_root  tree;
-+      } au_si_pid;
++      struct au_si_pid        au_si_pid;
 +
 +      /*
 +       * dirty approach to protect sb->sb_inodes and ->s_files (gone) from
@@ -27986,9 +27971,6 @@ diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 +      /* include/asm-ia64/siginfo.h defines a macro named si_flags */
 +      unsigned int            si_mntflags;
 +
-+      /* symlink to follow_link() and put_link() */
-+      struct au_sphlhead      si_symlink;
-+
 +      /* external inode number (bitmap and translation table) */
 +      vfs_readf_t             si_xread;
 +      vfs_writef_t            si_xwrite;
@@ -28144,10 +28126,6 @@ diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 +int aufs_read_and_write_lock2(struct dentry *d1, struct dentry *d2, int flags);
 +void aufs_read_and_write_unlock2(struct dentry *d1, struct dentry *d2);
 +
-+int si_pid_test_slow(struct super_block *sb);
-+void si_pid_set_slow(struct super_block *sb);
-+void si_pid_clr_slow(struct super_block *sb);
-+
 +/* wbr_policy.c */
 +extern struct au_wbr_copyup_operations au_wbr_copyup_ops[];
 +extern struct au_wbr_create_operations au_wbr_create_ops[];
@@ -28295,48 +28273,43 @@ diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 +
 +/* ---------------------------------------------------------------------- */
 +
-+static inline pid_t si_pid_bit(void)
++static inline void si_pid_idx_bit(int *idx, pid_t *bit)
 +{
 +      /* the origin of pid is 1, but the bitmap's is 0 */
-+      return current->pid - 1;
++      *bit = current->pid - 1;
++      *idx = *bit / AU_PIDSTEP;
++      *bit %= AU_PIDSTEP;
 +}
 +
 +static inline int si_pid_test(struct super_block *sb)
 +{
 +      pid_t bit;
++      int idx;
++      unsigned long *bitmap;
 +
-+      bit = si_pid_bit();
-+      if (bit < PID_MAX_DEFAULT)
-+              return test_bit(bit, au_sbi(sb)->au_si_pid.bitmap);
-+      return si_pid_test_slow(sb);
-+}
-+
-+static inline void si_pid_set(struct super_block *sb)
-+{
-+      pid_t bit;
-+
-+      bit = si_pid_bit();
-+      if (bit < PID_MAX_DEFAULT) {
-+              AuDebugOn(test_bit(bit, au_sbi(sb)->au_si_pid.bitmap));
-+              set_bit(bit, au_sbi(sb)->au_si_pid.bitmap);
-+              /* smp_mb(); */
-+      } else
-+              si_pid_set_slow(sb);
++      si_pid_idx_bit(&idx, &bit);
++      bitmap = au_sbi(sb)->au_si_pid.pid_bitmap[idx];
++      if (bitmap)
++              return test_bit(bit, bitmap);
++      return 0;
 +}
 +
 +static inline void si_pid_clr(struct super_block *sb)
 +{
 +      pid_t bit;
++      int idx;
++      unsigned long *bitmap;
 +
-+      bit = si_pid_bit();
-+      if (bit < PID_MAX_DEFAULT) {
-+              AuDebugOn(!test_bit(bit, au_sbi(sb)->au_si_pid.bitmap));
-+              clear_bit(bit, au_sbi(sb)->au_si_pid.bitmap);
-+              /* smp_mb(); */
-+      } else
-+              si_pid_clr_slow(sb);
++      si_pid_idx_bit(&idx, &bit);
++      bitmap = au_sbi(sb)->au_si_pid.pid_bitmap[idx];
++      BUG_ON(!bitmap);
++      AuDebugOn(!test_bit(bit, bitmap));
++      clear_bit(bit, bitmap);
++      /* smp_mb(); */
 +}
 +
++void si_pid_set(struct super_block *sb);
++
 +/* ---------------------------------------------------------------------- */
 +
 +/* lock superblock. mainly for entry point functions */
@@ -28484,7 +28457,7 @@ diff -urN /usr/share/empty/fs/aufs/super.h linux/fs/aufs/super.h
 +#endif /* __AUFS_SUPER_H__ */
 diff -urN /usr/share/empty/fs/aufs/sysaufs.c linux/fs/aufs/sysaufs.c
 --- /usr/share/empty/fs/aufs/sysaufs.c 1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/sysaufs.c    2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/sysaufs.c    2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,104 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -28592,7 +28565,7 @@ diff -urN /usr/share/empty/fs/aufs/sysaufs.c linux/fs/aufs/sysaufs.c
 +}
 diff -urN /usr/share/empty/fs/aufs/sysaufs.h linux/fs/aufs/sysaufs.h
 --- /usr/share/empty/fs/aufs/sysaufs.h 1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/sysaufs.h    2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/sysaufs.h    2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,101 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -28697,7 +28670,7 @@ diff -urN /usr/share/empty/fs/aufs/sysaufs.h linux/fs/aufs/sysaufs.h
 +#endif /* __SYSAUFS_H__ */
 diff -urN /usr/share/empty/fs/aufs/sysfs.c linux/fs/aufs/sysfs.c
 --- /usr/share/empty/fs/aufs/sysfs.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/sysfs.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/sysfs.c      2016-04-24 18:32:51.393686895 +0200
 @@ -0,0 +1,376 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -29077,7 +29050,7 @@ diff -urN /usr/share/empty/fs/aufs/sysfs.c linux/fs/aufs/sysfs.c
 +}
 diff -urN /usr/share/empty/fs/aufs/sysrq.c linux/fs/aufs/sysrq.c
 --- /usr/share/empty/fs/aufs/sysrq.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/sysrq.c      2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/sysrq.c      2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,157 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -29238,7 +29211,7 @@ diff -urN /usr/share/empty/fs/aufs/sysrq.c linux/fs/aufs/sysrq.c
 +}
 diff -urN /usr/share/empty/fs/aufs/vdir.c linux/fs/aufs/vdir.c
 --- /usr/share/empty/fs/aufs/vdir.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/vdir.c       2016-02-28 11:26:32.573304539 +0100
++++ linux/fs/aufs/vdir.c       2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,888 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -30130,8 +30103,8 @@ diff -urN /usr/share/empty/fs/aufs/vdir.c linux/fs/aufs/vdir.c
 +}
 diff -urN /usr/share/empty/fs/aufs/vfsub.c linux/fs/aufs/vfsub.c
 --- /usr/share/empty/fs/aufs/vfsub.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/vfsub.c      2016-02-28 11:26:32.573304539 +0100
-@@ -0,0 +1,866 @@
++++ linux/fs/aufs/vfsub.c      2016-04-24 18:32:51.397020264 +0200
+@@ -0,0 +1,884 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -30289,6 +30262,24 @@ diff -urN /usr/share/empty/fs/aufs/vfsub.c linux/fs/aufs/vfsub.c
 +      return err;
 +}
 +
++struct dentry *vfsub_lookup_one_len_unlocked(const char *name,
++                                           struct dentry *parent, int len)
++{
++      struct path path = {
++              .mnt = NULL
++      };
++
++      path.dentry = lookup_one_len_unlocked(name, parent, len);
++      if (IS_ERR(path.dentry))
++              goto out;
++      if (d_is_positive(path.dentry))
++              vfsub_update_h_iattr(&path, /*did*/NULL); /*ignore*/
++
++out:
++      AuTraceErrPtr(path.dentry);
++      return path.dentry;
++}
++
 +struct dentry *vfsub_lookup_one_len(const char *name, struct dentry *parent,
 +                                  int len)
 +{
@@ -31000,8 +30991,8 @@ diff -urN /usr/share/empty/fs/aufs/vfsub.c linux/fs/aufs/vfsub.c
 +}
 diff -urN /usr/share/empty/fs/aufs/vfsub.h linux/fs/aufs/vfsub.h
 --- /usr/share/empty/fs/aufs/vfsub.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/vfsub.h      2016-02-28 11:26:32.576637942 +0100
-@@ -0,0 +1,308 @@
++++ linux/fs/aufs/vfsub.h      2016-04-24 18:32:51.397020264 +0200
+@@ -0,0 +1,310 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
 + *
@@ -31056,7 +31047,7 @@ diff -urN /usr/share/empty/fs/aufs/vfsub.h linux/fs/aufs/vfsub.h
 +
 +/* to debug easier, do not make them inlined functions */
 +#define MtxMustLock(mtx)      AuDebugOn(!mutex_is_locked(mtx))
-+#define IMustLock(i)          MtxMustLock(&(i)->i_mutex)
++#define IMustLock(i)          AuDebugOn(!inode_is_locked(i))
 +
 +/* ---------------------------------------------------------------------- */
 +
@@ -31103,6 +31094,8 @@ diff -urN /usr/share/empty/fs/aufs/vfsub.h linux/fs/aufs/vfsub.h
 +                    struct vfsub_aopen_args *args, struct au_branch *br);
 +int vfsub_kern_path(const char *name, unsigned int flags, struct path *path);
 +
++struct dentry *vfsub_lookup_one_len_unlocked(const char *name,
++                                           struct dentry *parent, int len);
 +struct dentry *vfsub_lookup_one_len(const char *name, struct dentry *parent,
 +                                  int len);
 +
@@ -31312,7 +31305,7 @@ diff -urN /usr/share/empty/fs/aufs/vfsub.h linux/fs/aufs/vfsub.h
 +#endif /* __AUFS_VFSUB_H__ */
 diff -urN /usr/share/empty/fs/aufs/wbr_policy.c linux/fs/aufs/wbr_policy.c
 --- /usr/share/empty/fs/aufs/wbr_policy.c      1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/wbr_policy.c 2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/wbr_policy.c 2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,765 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -31456,17 +31449,17 @@ diff -urN /usr/share/empty/fs/aufs/wbr_policy.c linux/fs/aufs/wbr_policy.c
 +      if (!au_ftest_cpdown(*flags, PARENT_OPQ) && bopq <= bdst)
 +              au_fset_cpdown(*flags, PARENT_OPQ);
 +      h_inode = d_inode(h_path.dentry);
-+      mutex_lock_nested(&h_inode->i_mutex, AuLsc_I_CHILD);
++      inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +      if (au_ftest_cpdown(*flags, WHED)) {
 +              err = au_cpdown_dir_opq(dentry, bdst, flags);
 +              if (unlikely(err)) {
-+                      mutex_unlock(&h_inode->i_mutex);
++                      inode_unlock(h_inode);
 +                      goto out_dir;
 +              }
 +      }
 +
 +      err = au_cpdown_attr(&h_path, au_h_dptr(dentry, bstart));
-+      mutex_unlock(&h_inode->i_mutex);
++      inode_unlock(h_inode);
 +      if (unlikely(err))
 +              goto out_opq;
 +
@@ -31487,9 +31480,9 @@ diff -urN /usr/share/empty/fs/aufs/wbr_policy.c linux/fs/aufs/wbr_policy.c
 +      /* revert */
 +out_opq:
 +      if (au_ftest_cpdown(*flags, DIROPQ)) {
-+              mutex_lock_nested(&h_inode->i_mutex, AuLsc_I_CHILD);
++              inode_lock_nested(h_inode, AuLsc_I_CHILD);
 +              rerr = au_diropq_remove(dentry, bdst);
-+              mutex_unlock(&h_inode->i_mutex);
++              inode_unlock(h_inode);
 +              if (unlikely(rerr)) {
 +                      AuIOErr("failed removing diropq for %pd b%d (%d)\n",
 +                              dentry, bdst, rerr);
@@ -32081,7 +32074,7 @@ diff -urN /usr/share/empty/fs/aufs/wbr_policy.c linux/fs/aufs/wbr_policy.c
 +};
 diff -urN /usr/share/empty/fs/aufs/whout.c linux/fs/aufs/whout.c
 --- /usr/share/empty/fs/aufs/whout.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/whout.c      2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/whout.c      2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,1060 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -33027,7 +33020,7 @@ diff -urN /usr/share/empty/fs/aufs/whout.c linux/fs/aufs/whout.c
 +
 +      br = au_sbr(dir->i_sb, bindex);
 +      wh_inode = d_inode(wh_dentry);
-+      mutex_lock_nested(&wh_inode->i_mutex, AuLsc_I_CHILD);
++      inode_lock_nested(wh_inode, AuLsc_I_CHILD);
 +
 +      /*
 +       * someone else might change some whiteouts while we were sleeping.
@@ -33049,7 +33042,7 @@ diff -urN /usr/share/empty/fs/aufs/whout.c linux/fs/aufs/whout.c
 +              if (unlikely(wkq_err))
 +                      err = wkq_err;
 +      }
-+      mutex_unlock(&wh_inode->i_mutex);
++      inode_unlock(wh_inode);
 +
 +      if (!err) {
 +              h_tmp.dentry = wh_dentry;
@@ -33085,7 +33078,7 @@ diff -urN /usr/share/empty/fs/aufs/whout.c linux/fs/aufs/whout.c
 +      struct au_hinode *hdir;
 +
 +      /* rmdir by nfsd may cause deadlock with this i_mutex */
-+      /* mutex_lock(&a->dir->i_mutex); */
++      /* inode_lock(a->dir); */
 +      err = -EROFS;
 +      sb = a->dir->i_sb;
 +      si_read_lock(sb, !AuLock_FLUSH);
@@ -33115,7 +33108,7 @@ diff -urN /usr/share/empty/fs/aufs/whout.c linux/fs/aufs/whout.c
 +      dput(h_parent);
 +      ii_write_unlock(a->dir);
 +out:
-+      /* mutex_unlock(&a->dir->i_mutex); */
++      /* inode_unlock(a->dir); */
 +      au_whtmp_rmdir_free(a);
 +      si_read_unlock(sb);
 +      au_nwt_done(&au_sbi(sb)->si_nowait);
@@ -33145,7 +33138,7 @@ diff -urN /usr/share/empty/fs/aufs/whout.c linux/fs/aufs/whout.c
 +}
 diff -urN /usr/share/empty/fs/aufs/whout.h linux/fs/aufs/whout.h
 --- /usr/share/empty/fs/aufs/whout.h   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/whout.h      2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/whout.h      2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,85 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -33234,7 +33227,7 @@ diff -urN /usr/share/empty/fs/aufs/whout.h linux/fs/aufs/whout.h
 +#endif /* __AUFS_WHOUT_H__ */
 diff -urN /usr/share/empty/fs/aufs/wkq.c linux/fs/aufs/wkq.c
 --- /usr/share/empty/fs/aufs/wkq.c     1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/wkq.c        2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/wkq.c        2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,213 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -33451,7 +33444,7 @@ diff -urN /usr/share/empty/fs/aufs/wkq.c linux/fs/aufs/wkq.c
 +}
 diff -urN /usr/share/empty/fs/aufs/wkq.h linux/fs/aufs/wkq.h
 --- /usr/share/empty/fs/aufs/wkq.h     1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/wkq.h        2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/wkq.h        2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,91 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -33546,7 +33539,7 @@ diff -urN /usr/share/empty/fs/aufs/wkq.h linux/fs/aufs/wkq.h
 +#endif /* __AUFS_WKQ_H__ */
 diff -urN /usr/share/empty/fs/aufs/xattr.c linux/fs/aufs/xattr.c
 --- /usr/share/empty/fs/aufs/xattr.c   1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/xattr.c      2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/xattr.c      2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,344 @@
 +/*
 + * Copyright (C) 2014-2016 Junjiro R. Okajima
@@ -33638,9 +33631,9 @@ diff -urN /usr/share/empty/fs/aufs/xattr.c linux/fs/aufs/xattr.c
 +
 +      /* unlock it temporary */
 +      h_idst = d_inode(h_dst);
-+      mutex_unlock(&h_idst->i_mutex);
++      inode_unlock(h_idst);
 +      err = vfsub_setxattr(h_dst, name, *buf, ssz, /*flags*/0);
-+      mutex_lock_nested(&h_idst->i_mutex, AuLsc_I_CHILD2);
++      inode_lock_nested(h_idst, AuLsc_I_CHILD2);
 +      if (unlikely(err)) {
 +              if (verbose || au_debug_test())
 +                      pr_err("%s, err %d\n", name, err);
@@ -33663,9 +33656,9 @@ diff -urN /usr/share/empty/fs/aufs/xattr.c linux/fs/aufs/xattr.c
 +      /* there should not be the parent-child relationship between them */
 +      h_isrc = d_inode(h_src);
 +      h_idst = d_inode(h_dst);
-+      mutex_unlock(&h_idst->i_mutex);
-+      mutex_lock_nested(&h_isrc->i_mutex, AuLsc_I_CHILD);
-+      mutex_lock_nested(&h_idst->i_mutex, AuLsc_I_CHILD2);
++      inode_unlock(h_idst);
++      inode_lock_nested(h_isrc, AuLsc_I_CHILD);
++      inode_lock_nested(h_idst, AuLsc_I_CHILD2);
 +      unlocked = 0;
 +
 +      /* some filesystems don't list POSIX ACL, for example tmpfs */
@@ -33690,7 +33683,7 @@ diff -urN /usr/share/empty/fs/aufs/xattr.c linux/fs/aufs/xattr.c
 +                      goto out;
 +              err = vfs_listxattr(h_src, p, ssz);
 +      }
-+      mutex_unlock(&h_isrc->i_mutex);
++      inode_unlock(h_isrc);
 +      unlocked = 1;
 +      AuDbg("err %d, ssz %zd\n", err, ssz);
 +      if (unlikely(err < 0))
@@ -33732,7 +33725,7 @@ diff -urN /usr/share/empty/fs/aufs/xattr.c linux/fs/aufs/xattr.c
 +      kfree(o);
 +out:
 +      if (!unlocked)
-+              mutex_unlock(&h_isrc->i_mutex);
++              inode_unlock(h_isrc);
 +      AuTraceErr(err);
 +      return err;
 +}
@@ -33894,7 +33887,7 @@ diff -urN /usr/share/empty/fs/aufs/xattr.c linux/fs/aufs/xattr.c
 +#endif
 diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 --- /usr/share/empty/fs/aufs/xino.c    1970-01-01 01:00:00.000000000 +0100
-+++ linux/fs/aufs/xino.c       2016-02-28 11:26:32.576637942 +0100
++++ linux/fs/aufs/xino.c       2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,1318 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -34128,7 +34121,7 @@ diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 +struct au_xino_lock_dir {
 +      struct au_hinode *hdir;
 +      struct dentry *parent;
-+      struct mutex *mtx;
++      struct inode *dir;
 +};
 +
 +static void au_xino_lock_dir(struct super_block *sb, struct file *xino,
@@ -34146,8 +34139,8 @@ diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 +              au_hn_imtx_lock_nested(ldir->hdir, AuLsc_I_PARENT);
 +      } else {
 +              ldir->parent = dget_parent(xino->f_path.dentry);
-+              ldir->mtx = &d_inode(ldir->parent)->i_mutex;
-+              mutex_lock_nested(ldir->mtx, AuLsc_I_PARENT);
++              ldir->dir = d_inode(ldir->parent);
++              inode_lock_nested(ldir->dir, AuLsc_I_PARENT);
 +      }
 +}
 +
@@ -34156,7 +34149,7 @@ diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 +      if (ldir->hdir)
 +              au_hn_imtx_unlock(ldir->hdir);
 +      else {
-+              mutex_unlock(ldir->mtx);
++              inode_unlock(ldir->dir);
 +              dput(ldir->parent);
 +      }
 +}
@@ -34671,13 +34664,13 @@ diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 +      inode = file_inode(file);
 +      h_parent = dget_parent(file->f_path.dentry);
 +      h_dir = d_inode(h_parent);
-+      mutex_lock_nested(&h_dir->i_mutex, AuLsc_I_PARENT);
++      inode_lock_nested(h_dir, AuLsc_I_PARENT);
 +      /* mnt_want_write() is unnecessary here */
 +      /* no delegation since it is just created */
 +      if (inode->i_nlink)
 +              err = vfsub_unlink(h_dir, &file->f_path, /*delegated*/NULL,
 +                                 /*force*/0);
-+      mutex_unlock(&h_dir->i_mutex);
++      inode_unlock(h_dir);
 +      dput(h_parent);
 +      if (unlikely(err)) {
 +              if (!silent)
@@ -35112,14 +35105,14 @@ diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 +
 +      au_opt_set(sbinfo->si_mntflags, XINO);
 +      dir = d_inode(parent);
-+      mutex_lock_nested(&dir->i_mutex, AuLsc_I_PARENT);
++      inode_lock_nested(dir, AuLsc_I_PARENT);
 +      /* mnt_want_write() is unnecessary here */
 +      err = au_xino_set_xib(sb, xino->file);
 +      if (!err)
 +              err = au_xigen_set(sb, xino->file);
 +      if (!err)
 +              err = au_xino_set_br(sb, xino->file);
-+      mutex_unlock(&dir->i_mutex);
++      inode_unlock(dir);
 +      if (!err)
 +              goto out; /* success */
 +
@@ -35216,7 +35209,7 @@ diff -urN /usr/share/empty/fs/aufs/xino.c linux/fs/aufs/xino.c
 +}
 diff -urN /usr/share/empty/include/uapi/linux/aufs_type.h linux/include/uapi/linux/aufs_type.h
 --- /usr/share/empty/include/uapi/linux/aufs_type.h    1970-01-01 01:00:00.000000000 +0100
-+++ linux/include/uapi/linux/aufs_type.h       2016-02-28 11:26:32.576637942 +0100
++++ linux/include/uapi/linux/aufs_type.h       2016-04-24 18:32:51.397020264 +0200
 @@ -0,0 +1,419 @@
 +/*
 + * Copyright (C) 2005-2016 Junjiro R. Okajima
@@ -35259,7 +35252,7 @@ diff -urN /usr/share/empty/include/uapi/linux/aufs_type.h linux/include/uapi/lin
 +
 +#include <linux/limits.h>
 +
-+#define AUFS_VERSION  "4.4-20160223"
++#define AUFS_VERSION  "4.5-20160328"
 +
 +/* todo? move this to linux-2.6.19/include/magic.h */
 +#define AUFS_SUPER_MAGIC      ('a' << 24 | 'u' << 16 | 'f' << 8 | 's')
@@ -35637,10 +35630,10 @@ diff -urN /usr/share/empty/include/uapi/linux/aufs_type.h linux/include/uapi/lin
 +#define AUFS_CTL_FHSM_FD      _IOW(AuCtlType, AuCtl_FHSM_FD, int)
 +
 +#endif /* __AUFS_TYPE_H__ */
-aufs4.4 loopback patch
+aufs4.5 loopback patch
 
 diff --git a/drivers/block/loop.c b/drivers/block/loop.c
-index abfdd2b..a2e3c43 100644
+index 0b816b2..86dd454 100644
 --- a/drivers/block/loop.c
 +++ b/drivers/block/loop.c
 @@ -556,7 +556,7 @@ static int do_req_filebacked(struct loop_device *lo, struct request *rq)
@@ -35819,7 +35812,7 @@ index fb2237c..c3888c5 100644
        unsigned        lo_blocksize;
        void            *key_data; 
 diff --git a/fs/aufs/f_op.c b/fs/aufs/f_op.c
-index 2baacd7..22bcb89 100644
+index ac1304a..0cefd8a 100644
 --- a/fs/aufs/f_op.c
 +++ b/fs/aufs/f_op.c
 @@ -399,7 +399,7 @@ static ssize_t aufs_splice_read(struct file *file, loff_t *ppos,
@@ -35881,7 +35874,7 @@ index 48bf070..66afec7 100644
  
  #endif /* __KERNEL__ */
 diff --git a/fs/aufs/super.c b/fs/aufs/super.c
-index b41d789..51d2fb9 100644
+index 7928a50..9466cc9 100644
 --- a/fs/aufs/super.c
 +++ b/fs/aufs/super.c
 @@ -832,7 +832,10 @@ static const struct super_operations aufs_sop = {
@@ -35897,10 +35890,10 @@ index b41d789..51d2fb9 100644
  
  /* ---------------------------------------------------------------------- */
 diff --git a/include/linux/fs.h b/include/linux/fs.h
-index 8d48506..5246785 100644
+index 99fc2bd..842a2e0 100644
 --- a/include/linux/fs.h
 +++ b/include/linux/fs.h
-@@ -1719,6 +1719,10 @@ struct super_operations {
+@@ -1759,6 +1759,10 @@ struct super_operations {
                                  struct shrink_control *);
        long (*free_cached_objects)(struct super_block *,
                                    struct shrink_control *);
This page took 0.238722 seconds and 4 git commands to generate.