diff options
author | Andy Whitcroft <apw@canonical.com> | 2011-05-16 11:04:39 +0100 |
---|---|---|
committer | John Rigby <john.rigby@linaro.org> | 2011-11-16 14:24:18 -0700 |
commit | d09bba867f764b36afdd6203eb2984e7b6292e48 (patch) | |
tree | 9c64f0844f8700f411988651a1627a7acfadcce7 /ubuntu | |
parent | a1e5843c0d882b7bca9cebc86d065e89cb24a9fd (diff) |
UBUNTU: ubuntu: AUFS -- update to c6b76974311efc5bf3eddf921cd015b6aae46935
Remaining Ubuntu Changes:
UBUNTU: ubuntu: AUFS -- suppress benign plink warning messages
Upstream Changelog:
commit c6b76974311efc5bf3eddf921cd015b6aae46935
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 15 18:14:01 2011 +0900
aufs: for .38, replace dcache_lock by i_lock
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 02687391b4084d24af377a774ae25911df49b9e3
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Thu Apr 14 10:47:58 2011 +0900
aufs: possible bugfix, aufs_link supports for a flushed plink
In aufs_link(), the given dentry may be a psuedo-link. In this case,
aufs should detect it and call vfs_link() for the real inode on the
highest branch.
A new function au_h_d_alias() is introduced.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit a74d7008d25093b5d1fecb7f33df98570fddbf7e
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Apr 13 23:10:40 2011 +0900
aufs: debug, new debug print au_dpri_dalias
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit ad8f42b1ece790644d3a050907009a48153de71c
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Tue Apr 12 23:38:58 2011 +0900
aufs: possible bugfix, decode_by_ino support for obsolete dentry
In decoding the NFS file handle, the cached dentry may be obsoleted by
aufs branch mgmt. To support this case, decode_by_ino() returns NULL to
force falling to the next level of decoding, eg decode_by_dir_ino.
In decode_by_dir_ino(), a new lookup is issued and the dentry will be
refreshed.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 1f2bca01f562d4247494bbf20bcd8860b341d30c
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Thu Apr 7 22:07:34 2011 +0900
aufs: tiny, note about ./include/linux/Kbuild
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 2bc4f0f5c84d7f06f24afc30a3d527b6c5762bdf
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Thu Apr 7 00:25:09 2011 +0900
aufs: for 2.6.39, more lockdep mgmt
a missing lockdep_off/on().
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 27e557259bad6ebc48d4a811d5ef9db94070aa8b
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Mon Apr 4 02:35:07 2011 +0900
aufs: tiny, delete an unnecessary space
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit cfab7ccc2ecc838898a3f1a6bb6203ac433791a9
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 14:25:49 2011 +0900
aufs: for 2.6.39, lockdep upgrades
Simply insert lockdef_off/on() calls in "sub-VFS" character of aufs.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 17eac367b03334e57a93e8051eb712add24d2534
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 16:31:22 2011 +0900
aufs: for 2.6.39, limit the support for IMA
Since it acquires i_mutex and causes a deadlock, replace a
ima_file_check() call by i_readcount_inc().
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 4b09fd3cf305c00199059dddb977eea15b43bd47
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 14:18:28 2011 +0900
aufs: for 2.6.39, a_op->sync_page is removed
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 8c6f250f54267fd05c2213d5e4a424ea5927dc3b
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 14:17:44 2011 +0900
aufs stdalone: for 2.6.39, CONFIG_EXPORTFS becomes boolean
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 0932903afb6ceda5523240a9187b7896c446432d
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 14:17:03 2011 +0900
aufs stdalone: for 2.6.39, export inode_sb_list_lock
The role of inode_lock is split into several locks.
Simply aufs follows it.
Export inode_sb_list_lock for modules.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 102c58ce81b28613a53b65657bc45e6c52d56534
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 14:16:22 2011 +0900
aufs: for 2.6.39, split inode_lock into several locks
The role of inode_lock was split into several locks.
Simply aufs follows it.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit a2235254f63941d7bcd4099bfbabd134465c3600
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Fri Apr 1 14:11:11 2011 +0900
aufs: for 2.6.39, replace __lookup_one_len by vfsub_name_hash
By the commit,
6a96ba5 2011-03-14 kill __lookup_one_len()
the function was removed and merged into lookup_one_len().
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 5ec0835848ad10501993a1ef21ab69c9a6a6b01c
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Tue Mar 29 16:26:35 2011 +0900
aufs: tiny, support for new fmode macros
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 26a0f8af5829c88d42db3446ae3778127c7a3f0c
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Mar 23 02:27:17 2011 +0900
aufs: version string for aufs2.1-39
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit eef0b4de3c91b95cb48d33286500a486ea3f4424
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Mar 23 02:13:27 2011 +0900
aufs: version string for aufs2.1-38
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit b7f6b930cc0671ccbd7ba4cc0f3aff35ee995834
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Tue Mar 22 23:43:56 2011 +0900
aufs: update donators
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 1c0c29f20a09d1767bfb97348f28b23a056ca5c7
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Mar 2 13:36:35 2011 +0900
aufs: refine a mutex for mmap 3/3, add a condition
Acquire fi_mmap mutex lock only when necessary, ie. the file is not
mmapped yet.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 6c4dbe7a9a28134e0246bafbcbdfac1614539fbd
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Mar 2 13:34:55 2011 +0900
aufs: refine a mutex for mmap 2/3, replace lockdep_off by dep_map
Since it can hide an important debug message, calling lockdep_off/on is
a bad approach. But aufs_mmap() does it in switching the owner of
fi_mmap mutex lock. Delegating a top-half of aufs_mmap() and switching
the owner of fi_mmap is still an ugly approach, but I don't find another
way.
Without lockdep_off, the kernel debugging feature produces a false
message.
Stop calling lockdep_off/on, use lockdep_acquire/release instead thus we
can get benefit from the debugging feature.
This is slightly tricky and a feature for debugging only.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit dcdfe3b9d0e67b2a9636813d452159495d205e92
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Mar 2 13:26:14 2011 +0900
aufs: refine a mutex for mmap 1/3, move functions and make them static
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit dcb6ad5eba7d9ef18909068285eefbb1cfe5e589
Author: John Johansen <john.johansen@canonical.com>
Date: Mon Feb 28 22:19:38 2011 -0800
Fix aufs call of security_path_mknod
The security_path_mknod hook requires an encoded 'dev' for its 'dev' paramet
but aufs is calling security_path_mknod with a 'dev' that was already
converted by 'new_decode_dev(dev)'. However security_path_mknod and its
consumer TOMOYO is expecting 'dev' rather than 'new_decode_dev(dev)'.
This will result in TOMOYO doing new_decode_dev(new_decode_dev(dev))
(which is wrong) when security_path_mknod() is called from aufs' vfsub_mknod
Signed-off-by: Tetsuo Handa <penguin-kernel@I-love.SAKURA.ne.jp>
Signed-off-by: John Johansen <john.johansen@canonical.com>
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 36d328cd7d0a68b79b4cbc9dad0af7653b403d36
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Wed Feb 23 01:25:05 2011 +0900
aufs: update the donators list
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit f4f4f752d0e83a59b8b36cc6870ca8635ff6f8af
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Mon Feb 14 20:57:35 2011 +0900
aufs: tiny, support verbose by au_br_mod()
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 6c2bad0b72d2299476a6fa8f6a6da0b4a2e115eb
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Mon Feb 14 15:32:24 2011 +0900
aufs: new ioctl AUFS_CTL_IBUSY
This new ioctl interface receives an inode number and a branch index.
When the actual (hidden) ino on that branch is in use and makes the
branch busy (un-removable), returns the h_ino.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
commit 5c0aa28ddfc1510834a5eac418e71f242d6061c9
Author: J. R. Okajima <hooanon05@yahoo.co.jp>
Date: Mon Feb 14 14:22:18 2011 +0900
aufs: new functions to test EBUSY
Extract parts from test_dentry_busy() and test_inode_busy() and create
new helper functions au_test_dbusy() and au_test_ibusy().
These functions will be used by a new ioctl to test EBUSY in the future.
Signed-off-by: J. R. Okajima <hooanon05@yahoo.co.jp>
Signed-off-by: Andy Whitcroft <apw@canonical.com>
Diffstat (limited to 'ubuntu')
-rw-r--r-- | ubuntu/aufs/BOM | 2 | ||||
-rw-r--r-- | ubuntu/aufs/Kconfig | 2 | ||||
-rw-r--r-- | ubuntu/aufs/branch.c | 98 | ||||
-rw-r--r-- | ubuntu/aufs/branch.h | 4 | ||||
-rw-r--r-- | ubuntu/aufs/debug.c | 10 | ||||
-rw-r--r-- | ubuntu/aufs/debug.h | 7 | ||||
-rw-r--r-- | ubuntu/aufs/dentry.c | 2 | ||||
-rw-r--r-- | ubuntu/aufs/dentry.h | 1 | ||||
-rw-r--r-- | ubuntu/aufs/dinfo.c | 50 | ||||
-rw-r--r-- | ubuntu/aufs/dynop.c | 1 | ||||
-rw-r--r-- | ubuntu/aufs/export.c | 4 | ||||
-rw-r--r-- | ubuntu/aufs/f_op.c | 42 | ||||
-rw-r--r-- | ubuntu/aufs/file.c | 5 | ||||
-rw-r--r-- | ubuntu/aufs/file.h | 2 | ||||
-rw-r--r-- | ubuntu/aufs/finfo.c | 19 | ||||
-rw-r--r-- | ubuntu/aufs/i_op_add.c | 19 | ||||
-rw-r--r-- | ubuntu/aufs/ioctl.c | 8 | ||||
-rw-r--r-- | ubuntu/aufs/super.c | 16 | ||||
-rw-r--r-- | ubuntu/aufs/sysrq.c | 9 | ||||
-rw-r--r-- | ubuntu/aufs/vfsub.c | 108 | ||||
-rw-r--r-- | ubuntu/aufs/vfsub.h | 5 | ||||
-rw-r--r-- | ubuntu/aufs/xino.c | 4 | ||||
-rw-r--r-- | ubuntu/include/linux/aufs_type.h | 13 |
23 files changed, 334 insertions, 97 deletions
diff --git a/ubuntu/aufs/BOM b/ubuntu/aufs/BOM index 1d4f1617bb0..069c9f19c99 100644 --- a/ubuntu/aufs/BOM +++ b/ubuntu/aufs/BOM @@ -1,2 +1,2 @@ URL: http://git.c3sl.ufpr.br/pub/scm/aufs/aufs2-standalone.git -COMMIT: 65835da20b77c98fb538c9114fc31f5de1328230 +COMMIT: c6b76974311efc5bf3eddf921cd015b6aae46935 diff --git a/ubuntu/aufs/Kconfig b/ubuntu/aufs/Kconfig index 17f8f75a5a6..8ff2bf78a86 100644 --- a/ubuntu/aufs/Kconfig +++ b/ubuntu/aufs/Kconfig @@ -72,7 +72,7 @@ endchoice config AUFS_EXPORT bool "NFS-exportable aufs" - depends on (AUFS_FS = y && EXPORTFS = y) || (AUFS_FS = m && EXPORTFS) + depends on EXPORTFS help If you want to export your mounted aufs via NFS, then enable this option. There are several requirements for this configuration. diff --git a/ubuntu/aufs/branch.c b/ubuntu/aufs/branch.c index 3690dcba970..0c6aabc34dd 100644 --- a/ubuntu/aufs/branch.c +++ b/ubuntu/aufs/branch.c @@ -20,6 +20,7 @@ * branch management */ +#include <linux/compat.h> #include <linux/file.h> #include <linux/statfs.h> #include "aufs.h" @@ -530,6 +531,18 @@ out: pr_info(fmt, ##__VA_ARGS__); \ } while (0) +static int au_test_ibusy(struct inode *inode, aufs_bindex_t bstart, + aufs_bindex_t bend) +{ + return (inode && !S_ISDIR(inode->i_mode)) || bstart == bend; +} + +static int au_test_dbusy(struct dentry *dentry, aufs_bindex_t bstart, + aufs_bindex_t bend) +{ + return au_test_ibusy(dentry->d_inode, bstart, bend); +} + /* * test if the branch is deletable or not. */ @@ -541,7 +554,6 @@ static int test_dentry_busy(struct dentry *root, aufs_bindex_t bindex, struct au_dcsub_pages dpages; struct au_dpage *dpage; struct dentry *d; - struct inode *inode; err = au_dpages_init(&dpages, GFP_NOFS); if (unlikely(err)) @@ -578,14 +590,12 @@ static int test_dentry_busy(struct dentry *root, aufs_bindex_t bindex, } /* AuDbgDentry(d); */ - inode = d->d_inode; bstart = au_dbstart(d); bend = au_dbend(d); if (bstart <= bindex && bindex <= bend && au_h_dptr(d, bindex) - && ((inode && !S_ISDIR(inode->i_mode)) - || bstart == bend)) { + && au_test_dbusy(d, bstart, bend)) { err = -EBUSY; AuVerbose(verbose, "busy %.*s\n", AuDLNPair(d)); AuDbgDentry(d); @@ -640,7 +650,7 @@ static int test_inode_busy(struct super_block *sb, aufs_bindex_t bindex, if (bstart <= bindex && bindex <= bend && au_h_iptr(i, bindex) - && (!S_ISDIR(i->i_mode) || bstart == bend)) { + && au_test_ibusy(i, bstart, bend)) { err = -EBUSY; AuVerbose(verbose, "busy i%lu\n", i->i_ino); AuDbgInode(i); @@ -842,6 +852,77 @@ out: /* ---------------------------------------------------------------------- */ +static int au_ibusy(struct super_block *sb, struct aufs_ibusy __user *arg) +{ + int err; + aufs_bindex_t bstart, bend; + struct aufs_ibusy ibusy; + struct inode *inode, *h_inode; + + err = -EPERM; + if (unlikely(!capable(CAP_SYS_ADMIN))) + goto out; + + err = copy_from_user(&ibusy, arg, sizeof(ibusy)); + if (!err) + err = !access_ok(VERIFY_WRITE, &arg->h_ino, sizeof(arg->h_ino)); + if (unlikely(err)) { + err = -EFAULT; + AuTraceErr(err); + goto out; + } + + err = -EINVAL; + si_read_lock(sb, AuLock_FLUSH); + if (unlikely(ibusy.bindex < 0 || ibusy.bindex > au_sbend(sb))) + goto out_unlock; + + err = 0; + ibusy.h_ino = 0; /* invalid */ + inode = ilookup(sb, ibusy.ino); + if (!inode + || inode->i_ino == AUFS_ROOT_INO + || is_bad_inode(inode)) + goto out_unlock; + + ii_read_lock_child(inode); + bstart = au_ibstart(inode); + bend = au_ibend(inode); + if (bstart <= ibusy.bindex && ibusy.bindex <= bend) { + h_inode = au_h_iptr(inode, ibusy.bindex); + if (h_inode && au_test_ibusy(inode, bstart, bend)) + ibusy.h_ino = h_inode->i_ino; + } + ii_read_unlock(inode); + iput(inode); + +out_unlock: + si_read_unlock(sb); + if (!err) { + err = __put_user(ibusy.h_ino, &arg->h_ino); + if (unlikely(err)) { + err = -EFAULT; + AuTraceErr(err); + } + } +out: + return err; +} + +long au_ibusy_ioctl(struct file *file, unsigned long arg) +{ + return au_ibusy(file->f_dentry->d_sb, (void __user *)arg); +} + +#ifdef CONFIG_COMPAT +long au_ibusy_compat_ioctl(struct file *file, unsigned long arg) +{ + return au_ibusy(file->f_dentry->d_sb, compat_ptr(arg)); +} +#endif + +/* ---------------------------------------------------------------------- */ + /* * change a branch permission */ @@ -911,12 +992,17 @@ static void au_farray_free(struct file **a, unsigned long long max) static int au_br_mod_files_ro(struct super_block *sb, aufs_bindex_t bindex) { int err, do_warn; + unsigned int mnt_flags; unsigned long long ull, max; aufs_bindex_t br_id; + unsigned char verbose; struct file *file, *hf, **array; struct inode *inode; struct au_hfile *hfile; + mnt_flags = au_mntflags(sb); + verbose = !!au_opt_test(mnt_flags, VERBOSE); + array = au_farray_alloc(sb, &max); err = PTR_ERR(array); if (IS_ERR(array)) @@ -931,6 +1017,8 @@ static int au_br_mod_files_ro(struct super_block *sb, aufs_bindex_t bindex) fi_read_lock(file); if (unlikely(au_test_mmapped(file))) { err = -EBUSY; + AuVerbose(verbose, "mmapped %.*s\n", + AuDLNPair(file->f_dentry)); AuDbgFile(file); FiMustNoWaiters(file); fi_read_unlock(file); diff --git a/ubuntu/aufs/branch.h b/ubuntu/aufs/branch.h index fdcaca2cd9f..4fa2b29c636 100644 --- a/ubuntu/aufs/branch.h +++ b/ubuntu/aufs/branch.h @@ -147,6 +147,10 @@ struct au_opt_add; int au_br_add(struct super_block *sb, struct au_opt_add *add, int remount); struct au_opt_del; int au_br_del(struct super_block *sb, struct au_opt_del *del, int remount); +long au_ibusy_ioctl(struct file *file, unsigned long arg); +#ifdef CONFIG_COMPAT +long au_ibusy_compat_ioctl(struct file *file, unsigned long arg); +#endif struct au_opt_mod; int au_br_mod(struct super_block *sb, struct au_opt_mod *mod, int remount, int *do_refresh); diff --git a/ubuntu/aufs/debug.c b/ubuntu/aufs/debug.c index 7fea72ae7f6..0b51ff521b0 100644 --- a/ubuntu/aufs/debug.c +++ b/ubuntu/aufs/debug.c @@ -133,6 +133,16 @@ void au_dpri_inode(struct inode *inode) iinfo->ii_hinode[0 + bindex].hi_whdentry); } +void au_dpri_dalias(struct inode *inode) +{ + struct dentry *d; + + spin_lock(&inode->i_lock); + list_for_each_entry(d, &inode->i_dentry, d_alias) + au_dpri_dentry(d); + spin_unlock(&inode->i_lock); +} + static int do_pri_dentry(aufs_bindex_t bindex, struct dentry *dentry) { struct dentry *wh = NULL; diff --git a/ubuntu/aufs/debug.h b/ubuntu/aufs/debug.h index 1881844ec59..453459e664d 100644 --- a/ubuntu/aufs/debug.h +++ b/ubuntu/aufs/debug.h @@ -122,6 +122,7 @@ struct au_vdir; void au_dpri_vdir(struct au_vdir *vdir); struct inode; void au_dpri_inode(struct inode *inode); +void au_dpri_dalias(struct inode *inode); void au_dpri_dentry(struct dentry *dentry); struct file; void au_dpri_file(struct file *filp); @@ -156,6 +157,11 @@ void au_debug_sbinfo_init(struct au_sbinfo *sbinfo); au_dpri_inode(i); \ } while (0) +#define AuDbgDAlias(i) do { \ + AuDbg(#i "\n"); \ + au_dpri_dalias(i); \ +} while (0) + #define AuDbgDentry(d) do { \ AuDbg(#d "\n"); \ au_dpri_dentry(d); \ @@ -210,6 +216,7 @@ AuStubVoid(au_debug_sbinfo_init, struct au_sbinfo *sbinfo) #define AuDbgWhlist(w) do {} while (0) #define AuDbgVdir(v) do {} while (0) #define AuDbgInode(i) do {} while (0) +#define AuDbgDAlias(i) do {} while (0) #define AuDbgDentry(d) do {} while (0) #define AuDbgFile(f) do {} while (0) #define AuDbgSb(sb) do {} while (0) diff --git a/ubuntu/aufs/dentry.c b/ubuntu/aufs/dentry.c index 3c0d0ff0481..176fbdcd6ec 100644 --- a/ubuntu/aufs/dentry.c +++ b/ubuntu/aufs/dentry.c @@ -62,7 +62,7 @@ struct dentry *au_lkup_one(struct qstr *name, struct dentry *h_parent, h_nd.path.dentry = h_parent; h_nd.path.mnt = br->br_mnt; - err = __lookup_one_len(name->name, &h_nd.last, NULL, name->len); + err = vfsub_name_hash(name->name, &h_nd.last, name->len); h_dentry = ERR_PTR(err); if (!err) { path_get(&h_nd.path); diff --git a/ubuntu/aufs/dentry.h b/ubuntu/aufs/dentry.h index 8fd0eba055f..4f0827583c4 100644 --- a/ubuntu/aufs/dentry.h +++ b/ubuntu/aufs/dentry.h @@ -80,6 +80,7 @@ void di_write_lock2_parent(struct dentry *d1, struct dentry *d2, int isdir); void di_write_unlock2(struct dentry *d1, struct dentry *d2); struct dentry *au_h_dptr(struct dentry *dentry, aufs_bindex_t bindex); +struct dentry *au_h_d_alias(struct dentry *dentry, aufs_bindex_t bindex); aufs_bindex_t au_dbtail(struct dentry *dentry); aufs_bindex_t au_dbtaildir(struct dentry *dentry); diff --git a/ubuntu/aufs/dinfo.c b/ubuntu/aufs/dinfo.c index 17864425311..a2a6809ca7c 100644 --- a/ubuntu/aufs/dinfo.c +++ b/ubuntu/aufs/dinfo.c @@ -322,6 +322,56 @@ struct dentry *au_h_dptr(struct dentry *dentry, aufs_bindex_t bindex) return d; } +/* + * extended version of au_h_dptr(). + * returns a hashed and positive h_dentry in bindex, NULL, or error. + */ +struct dentry *au_h_d_alias(struct dentry *dentry, aufs_bindex_t bindex) +{ + struct dentry *h_dentry; + struct inode *inode, *h_inode; + + inode = dentry->d_inode; + AuDebugOn(!inode); + + h_dentry = NULL; + if (au_dbstart(dentry) <= bindex + && bindex <= au_dbend(dentry)) + h_dentry = au_h_dptr(dentry, bindex); + if (h_dentry && !au_d_hashed_positive(h_dentry)) { + dget(h_dentry); + goto out; /* success */ + } + + AuDebugOn(bindex < au_ibstart(inode)); + AuDebugOn(au_ibend(inode) < bindex); + h_inode = au_h_iptr(inode, bindex); + h_dentry = d_find_alias(h_inode); + if (h_dentry) { + if (!IS_ERR(h_dentry)) { + if (!au_d_hashed_positive(h_dentry)) + goto out; /* success */ + dput(h_dentry); + } else + goto out; + } + + if (au_opt_test(au_mntflags(dentry->d_sb), PLINK)) { + h_dentry = au_plink_lkup(inode, bindex); + AuDebugOn(!h_dentry); + if (!IS_ERR(h_dentry)) { + if (!au_d_hashed_positive(h_dentry)) + goto out; /* success */ + dput(h_dentry); + h_dentry = NULL; + } + } + +out: + AuDbgDentry(h_dentry); + return h_dentry; +} + aufs_bindex_t au_dbtail(struct dentry *dentry) { aufs_bindex_t bend, bwh; diff --git a/ubuntu/aufs/dynop.c b/ubuntu/aufs/dynop.c index 23b2691af7a..9241616332d 100644 --- a/ubuntu/aufs/dynop.c +++ b/ubuntu/aufs/dynop.c @@ -178,7 +178,6 @@ static void dy_aop(struct au_dykey *key, const void *h_op, DySetAop(writepage); DySetAopForce(readpage); /* force */ - DySetAop(sync_page); DySetAop(writepages); DySetAop(set_page_dirty); DySetAop(readpages); diff --git a/ubuntu/aufs/export.c b/ubuntu/aufs/export.c index 3a6ba18583e..05656fd1cf3 100644 --- a/ubuntu/aufs/export.c +++ b/ubuntu/aufs/export.c @@ -242,13 +242,15 @@ static struct dentry *decode_by_ino(struct super_block *sb, ino_t ino, spin_unlock(&inode->i_lock); } if (unlikely(dentry && au_digen_test(dentry, sigen))) { + /* need to refresh */ dput(dentry); - dentry = ERR_PTR(-ESTALE); + dentry = NULL; } out_iput: iput(inode); out: + AuTraceErrPtr(dentry); return dentry; } diff --git a/ubuntu/aufs/f_op.c b/ubuntu/aufs/f_op.c index aa8e3a88eb7..2a875768019 100644 --- a/ubuntu/aufs/f_op.c +++ b/ubuntu/aufs/f_op.c @@ -67,7 +67,7 @@ static int aufs_open_nondir(struct inode *inode __maybe_unused, int err; struct super_block *sb; - AuDbg("%.*s, f_ flags 0x%x, f_mode 0x%x\n", + AuDbg("%.*s, f_flags 0x%x, f_mode 0x%x\n", AuDLNPair(file->f_dentry), vfsub_file_flags(file), file->f_mode); @@ -225,7 +225,9 @@ static ssize_t au_do_aio(struct file *h_file, int rw, struct kiocb *kio, if (func) { file = kio->ki_filp; kio->ki_filp = h_file; + lockdep_off(); err = func(kio, iov, nv, pos); + lockdep_on(); kio->ki_filp = file; } else /* currently there is no such fs */ @@ -568,6 +570,33 @@ out: /* very ugly approach */ #include "mtx.h" +static void au_fi_mmap_lock_and_sell(struct file *file) +{ + struct mutex *mtx; + + FiMustWriteLock(file); + + mtx = &au_fi(file)->fi_mmap; + mutex_lock(mtx); + mutex_release(&mtx->dep_map, /*nested*/0, _RET_IP_); +} + +static void au_fi_mmap_buy(struct file *file) +{ + struct mutex *mtx; + + mtx = &au_fi(file)->fi_mmap; + MtxMustLock(mtx); + + mutex_set_owner(mtx); + mutex_acquire(&mtx->dep_map, /*subclass*/0, /*trylock*/0, _RET_IP_); +} + +static void au_fi_mmap_unlock(struct file *file) +{ + mutex_unlock(&au_fi(file)->fi_mmap); +} + struct au_mmap_pre_args { /* input */ struct file *file; @@ -613,7 +642,8 @@ static int au_mmap_pre(struct file *file, struct vm_area_struct *vma, *br = au_sbr(sb, bstart); *h_file = au_hf_top(file); get_file(*h_file); - au_fi_mmap_lock(file); + if (!*mmapped) + au_fi_mmap_lock_and_sell(file); out_unlock: fi_write_unlock(file); @@ -647,8 +677,8 @@ static int aufs_mmap(struct file *file, struct vm_area_struct *vma) err = wkq_err; if (unlikely(err)) goto out; - finfo = au_fi(file); - mutex_set_owner(&finfo->fi_mmap); + if (!args.mmapped) + au_fi_mmap_buy(file); h_dentry = args.h_file->f_dentry; if (!args.mmapped && au_test_fs_bad_mapping(h_dentry->d_sb)) { @@ -667,6 +697,7 @@ static int aufs_mmap(struct file *file, struct vm_area_struct *vma) err = PTR_ERR(h_vmop); if (IS_ERR(h_vmop)) goto out_unlock; + finfo = au_fi(file); AuDebugOn(args.mmapped && h_vmop != finfo->fi_hvmop); vmop = (void *)au_dy_vmop(file, args.br, h_vmop); @@ -695,7 +726,8 @@ static int aufs_mmap(struct file *file, struct vm_area_struct *vma) fsstack_copy_attr_atime(file->f_dentry->d_inode, h_dentry->d_inode); out_unlock: - au_fi_mmap_unlock(file); + if (!args.mmapped) + au_fi_mmap_unlock(file); fput(args.h_file); out: return err; diff --git a/ubuntu/aufs/file.c b/ubuntu/aufs/file.c index 27785ddc168..b798891953f 100644 --- a/ubuntu/aufs/file.c +++ b/ubuntu/aufs/file.c @@ -66,7 +66,7 @@ struct file *au_h_open(struct dentry *dentry, aufs_bindex_t bindex, int flags, sb = dentry->d_sb; br = au_sbr(sb, bindex); h_file = ERR_PTR(-EACCES); - exec_flag = flags & vfsub_fmode_to_uint(FMODE_EXEC); + exec_flag = flags & __FMODE_EXEC; if (exec_flag && (br->br_mnt->mnt_flags & MNT_NOEXEC)) goto out; @@ -633,8 +633,6 @@ static int aufs_write_end(struct file *file, struct address_space *mapping, { AuUnsupport(); return 0; } static int aufs_writepage(struct page *page, struct writeback_control *wbc) { AuUnsupport(); return 0; } -static void aufs_sync_page(struct page *page) -{ AuUnsupport(); } static int aufs_set_page_dirty(struct page *page) { AuUnsupport(); return 0; } @@ -662,7 +660,6 @@ const struct address_space_operations aufs_aop = { .get_xip_mem = aufs_get_xip_mem, #ifdef CONFIG_AUFS_DEBUG .writepage = aufs_writepage, - .sync_page = aufs_sync_page, /* no writepages, because of writepage */ .set_page_dirty = aufs_set_page_dirty, /* no readpages, because of readpage */ diff --git a/ubuntu/aufs/file.h b/ubuntu/aufs/file.h index 5ee45a10abd..7454a0e5e2b 100644 --- a/ubuntu/aufs/file.h +++ b/ubuntu/aufs/file.h @@ -129,8 +129,6 @@ void au_set_h_fptr(struct file *file, aufs_bindex_t bindex, struct file *h_file); void au_update_figen(struct file *file); -void au_fi_mmap_lock(struct file *file); -void au_fi_mmap_unlock(struct file *file); struct au_fidir *au_fidir_alloc(struct super_block *sb); int au_fidir_realloc(struct au_finfo *finfo, int nbr); diff --git a/ubuntu/aufs/finfo.c b/ubuntu/aufs/finfo.c index b8fa4d853a4..b3882063f34 100644 --- a/ubuntu/aufs/finfo.c +++ b/ubuntu/aufs/finfo.c @@ -26,7 +26,7 @@ void au_hfput(struct au_hfile *hf, struct file *file) { /* todo: direct access f_flags */ - if (vfsub_file_flags(file) & vfsub_fmode_to_uint(FMODE_EXEC)) + if (vfsub_file_flags(file) & __FMODE_EXEC) allow_write_access(hf->hf_file); fput(hf->hf_file); hf->hf_file = NULL; @@ -64,23 +64,6 @@ void au_update_figen(struct file *file) /* ---------------------------------------------------------------------- */ -void au_fi_mmap_lock(struct file *file) -{ - FiMustWriteLock(file); - lockdep_off(); - mutex_lock(&au_fi(file)->fi_mmap); - lockdep_on(); -} - -void au_fi_mmap_unlock(struct file *file) -{ - lockdep_off(); - mutex_unlock(&au_fi(file)->fi_mmap); - lockdep_on(); -} - -/* ---------------------------------------------------------------------- */ - struct au_fidir *au_fidir_alloc(struct super_block *sb) { struct au_fidir *fidir; diff --git a/ubuntu/aufs/i_op_add.c b/ubuntu/aufs/i_op_add.c index 070f6314ece..8bf18f496e2 100644 --- a/ubuntu/aufs/i_op_add.c +++ b/ubuntu/aufs/i_op_add.c @@ -453,6 +453,7 @@ static int au_cpup_or_link(struct dentry *src_dentry, struct au_link_args *a) au_plink_append(inode, a->bdst, a->h_path.dentry); out: + AuTraceErr(err); return err; } @@ -492,7 +493,7 @@ int aufs_link(struct dentry *src_dentry, struct inode *dir, goto out_unlock; a->src_parent = dget_parent(src_dentry); - wr_dir_args.force_btgt = au_dbstart(src_dentry); + wr_dir_args.force_btgt = au_ibstart(inode); di_write_lock_parent(a->parent); wr_dir_args.force_btgt = au_wbr(dentry, wr_dir_args.force_btgt); @@ -507,21 +508,29 @@ int aufs_link(struct dentry *src_dentry, struct inode *dir, a->bdst = au_dbstart(dentry); a->h_path.dentry = au_h_dptr(dentry, a->bdst); a->h_path.mnt = au_sbr_mnt(sb, a->bdst); - a->bsrc = au_dbstart(src_dentry); + a->bsrc = au_ibstart(inode); + h_src_dentry = au_h_d_alias(src_dentry, a->bsrc); + if (!h_src_dentry) { + a->bsrc = au_dbstart(src_dentry); + h_src_dentry = au_h_d_alias(src_dentry, a->bsrc); + AuDebugOn(!h_src_dentry); + } else if (IS_ERR(h_src_dentry)) + goto out_parent; + if (au_opt_test(au_mntflags(sb), PLINK)) { if (a->bdst < a->bsrc /* && h_src_dentry->d_sb != a->h_path.dentry->d_sb */) err = au_cpup_or_link(src_dentry, a); - else { - h_src_dentry = au_h_dptr(src_dentry, a->bdst); + else err = vfsub_link(h_src_dentry, au_pinned_h_dir(&a->pin), &a->h_path); - } + dput(h_src_dentry); } else { /* * copyup src_dentry to the branch we process, * and then link(2) to it. */ + dput(h_src_dentry); if (a->bdst < a->bsrc /* && h_src_dentry->d_sb != a->h_path.dentry->d_sb */) { au_unpin(&a->pin); diff --git a/ubuntu/aufs/ioctl.c b/ubuntu/aufs/ioctl.c index bb87a2229a8..e6695086dc5 100644 --- a/ubuntu/aufs/ioctl.c +++ b/ubuntu/aufs/ioctl.c @@ -91,6 +91,10 @@ long aufs_ioctl_dir(struct file *file, unsigned int cmd, unsigned long arg) err = au_wbr_fd(&file->f_path); break; + case AUFS_CTL_IBUSY: + err = au_ibusy_ioctl(file, arg); + break; + default: /* do not call the lower */ AuDbg("0x%x\n", cmd); @@ -132,6 +136,10 @@ long aufs_compat_ioctl_dir(struct file *file, unsigned int cmd, err = au_rdu_compat_ioctl(file, cmd, arg); break; + case AUFS_CTL_IBUSY: + err = au_ibusy_compat_ioctl(file, arg); + break; + default: err = aufs_ioctl_dir(file, cmd, arg); } diff --git a/ubuntu/aufs/super.c b/ubuntu/aufs/super.c index d5e0cd58087..bb5b1829d0e 100644 --- a/ubuntu/aufs/super.c +++ b/ubuntu/aufs/super.c @@ -450,17 +450,21 @@ static unsigned long long au_iarray_cb(void *a, n = 0; p = a; head = arg; - spin_lock(&inode_lock); + spin_lock(&inode_sb_list_lock); list_for_each_entry(inode, head, i_sb_list) { if (!is_bad_inode(inode) && au_ii(inode)->ii_bstart >= 0) { - au_igrab(inode); - *p++ = inode; - n++; - AuDebugOn(n > max); + spin_lock(&inode->i_lock); + if (atomic_read(&inode->i_count)) { + au_igrab(inode); + *p++ = inode; + n++; + AuDebugOn(n > max); + } + spin_unlock(&inode->i_lock); } } - spin_unlock(&inode_lock); + spin_unlock(&inode_sb_list_lock); return n; } diff --git a/ubuntu/aufs/sysrq.c b/ubuntu/aufs/sysrq.c index 99589d3048a..b427e477c02 100644 --- a/ubuntu/aufs/sysrq.c +++ b/ubuntu/aufs/sysrq.c @@ -76,11 +76,14 @@ static void sysrq_sb(struct super_block *sb) { struct inode *i; printk(KERN_WARNING AUFS_NAME ": isolated inode\n"); - spin_lock(&inode_lock); - list_for_each_entry(i, &sb->s_inodes, i_sb_list) + spin_lock(&inode_sb_list_lock); + list_for_each_entry(i, &sb->s_inodes, i_sb_list) { + spin_lock(&i->i_lock); if (1 || list_empty(&i->i_dentry)) au_dpri_inode(i); - spin_unlock(&inode_lock); + spin_unlock(&i->i_lock); + } + spin_unlock(&inode_sb_list_lock); } #endif printk(KERN_WARNING AUFS_NAME ": files\n"); diff --git a/ubuntu/aufs/vfsub.c b/ubuntu/aufs/vfsub.c index 40f6aefefa8..7b3cf55f342 100644 --- a/ubuntu/aufs/vfsub.c +++ b/ubuntu/aufs/vfsub.c @@ -50,51 +50,18 @@ int vfsub_update_h_iattr(struct path *h_path, int *did) /* ---------------------------------------------------------------------- */ -static int au_conv_oflags(int flags) -{ - int mask = 0; - -#ifdef CONFIG_IMA - fmode_t fmode; - - /* mask = MAY_OPEN; */ - fmode = OPEN_FMODE(flags); - if (fmode & FMODE_READ) - mask |= MAY_READ; - if ((fmode & FMODE_WRITE) - || (flags & O_TRUNC)) - mask |= MAY_WRITE; - /* - * if (flags & O_APPEND) - * mask |= MAY_APPEND; - */ - if (flags & vfsub_fmode_to_uint(FMODE_EXEC)) - mask |= MAY_EXEC; - - AuDbg("flags 0x%x, mask 0x%x\n", flags, mask); -#endif - - return mask; -} - struct file *vfsub_dentry_open(struct path *path, int flags) { struct file *file; - int err; path_get(path); file = dentry_open(path->dentry, path->mnt, - flags /* | vfsub_fmode_to_uint(FMODE_NONOTIFY) */, + flags /* | __FMODE_NONOTIFY */, current_cred()); - if (IS_ERR(file)) - goto out; + if (!IS_ERR_OR_NULL(file) + && (file->f_mode & (FMODE_READ | FMODE_WRITE)) == FMODE_READ) + i_readcount_inc(path->dentry->d_inode); - err = ima_file_check(file, au_conv_oflags(flags)); - if (unlikely(err)) { - fput(file); - file = ERR_PTR(err); - } -out: return file; } @@ -102,9 +69,11 @@ struct file *vfsub_filp_open(const char *path, int oflags, int mode) { struct file *file; + lockdep_off(); file = filp_open(path, - oflags /* | vfsub_fmode_to_uint(FMODE_NONOTIFY) */, + oflags /* | __FMODE_NONOTIFY */, mode); + lockdep_on(); if (IS_ERR(file)) goto out; vfsub_update_h_iattr(&file->f_path, /*did*/NULL); /*ignore*/ @@ -163,6 +132,34 @@ out: return path.dentry; } +/* + * this is "VFS:__lookup_one_len()" which was removed and merged into + * VFS:lookup_one_len() by the commit. + * 6a96ba5 2011-03-14 kill __lookup_one_len() + * this function should always be equivalent to the corresponding part in + * VFS:lookup_one_len(). + */ +int vfsub_name_hash(const char *name, struct qstr *this, int len) +{ + unsigned long hash; + unsigned int c; + + this->name = name; + this->len = len; + if (!len) + return -EACCES; + + hash = init_name_hash(); + while (len--) { + c = *(const unsigned char *)name++; + if (c == '/' || c == '\0') + return -EACCES; + hash = partial_name_hash(c, hash); + } + this->hash = end_name_hash(hash); + return 0; +} + /* ---------------------------------------------------------------------- */ struct dentry *vfsub_lock_rename(struct dentry *d1, struct au_hinode *hdir1, @@ -170,7 +167,9 @@ struct dentry *vfsub_lock_rename(struct dentry *d1, struct au_hinode *hdir1, { struct dentry *d; + lockdep_off(); d = lock_rename(d1, d2); + lockdep_on(); au_hn_suspend(hdir1); if (hdir1 != hdir2) au_hn_suspend(hdir2); @@ -184,7 +183,9 @@ void vfsub_unlock_rename(struct dentry *d1, struct au_hinode *hdir1, au_hn_resume(hdir1); if (hdir1 != hdir2) au_hn_resume(hdir2); + lockdep_off(); unlock_rename(d1, d2); + lockdep_on(); } /* ---------------------------------------------------------------------- */ @@ -326,7 +327,9 @@ int vfsub_link(struct dentry *src_dentry, struct inode *dir, struct path *path) if (unlikely(err)) goto out; + lockdep_off(); err = vfs_link(src_dentry, dir, path->dentry); + lockdep_on(); if (!err) { struct path tmp = *path; int did; @@ -366,7 +369,9 @@ int vfsub_rename(struct inode *src_dir, struct dentry *src_dentry, if (unlikely(err)) goto out; + lockdep_off(); err = vfs_rename(src_dir, src_dentry, dir, path->dentry); + lockdep_on(); if (!err) { int did; @@ -430,7 +435,9 @@ int vfsub_rmdir(struct inode *dir, struct path *path) if (unlikely(err)) goto out; + lockdep_off(); err = vfs_rmdir(dir, path->dentry); + lockdep_on(); if (!err) { struct path tmp = { .dentry = path->dentry->d_parent, @@ -451,7 +458,9 @@ ssize_t vfsub_read_u(struct file *file, char __user *ubuf, size_t count, { ssize_t err; + lockdep_off(); err = vfs_read(file, ubuf, count, ppos); + lockdep_on(); if (err >= 0) vfsub_update_h_iattr(&file->f_path, /*did*/NULL); /*ignore*/ return err; @@ -481,7 +490,9 @@ ssize_t vfsub_write_u(struct file *file, const char __user *ubuf, size_t count, { ssize_t err; + lockdep_off(); err = vfs_write(file, ubuf, count, ppos); + lockdep_on(); if (err >= 0) vfsub_update_h_iattr(&file->f_path, /*did*/NULL); /*ignore*/ return err; @@ -510,7 +521,13 @@ int vfsub_flush(struct file *file, fl_owner_t id) err = 0; if (file->f_op && file->f_op->flush) { - err = file->f_op->flush(file, id); + if (!au_test_nfs(file->f_dentry->d_sb)) + err = file->f_op->flush(file, id); + else { + lockdep_off(); + err = file->f_op->flush(file, id); + lockdep_on(); + } if (!err) vfsub_update_h_iattr(&file->f_path, /*did*/NULL); /*ignore*/ @@ -522,7 +539,9 @@ int vfsub_readdir(struct file *file, filldir_t filldir, void *arg) { int err; + lockdep_off(); err = vfs_readdir(file, filldir, arg); + lockdep_on(); if (err >= 0) vfsub_update_h_iattr(&file->f_path, /*did*/NULL); /*ignore*/ return err; @@ -534,7 +553,9 @@ long vfsub_splice_to(struct file *in, loff_t *ppos, { long err; + lockdep_off(); err = do_splice_to(in, ppos, pipe, len, flags); + lockdep_on(); file_accessed(in); if (err >= 0) vfsub_update_h_iattr(&in->f_path, /*did*/NULL); /*ignore*/ @@ -546,7 +567,9 @@ long vfsub_splice_from(struct pipe_inode_info *pipe, struct file *out, { long err; + lockdep_off(); err = do_splice_from(pipe, out, ppos, len, flags); + lockdep_on(); if (err >= 0) vfsub_update_h_iattr(&out->f_path, /*did*/NULL); /*ignore*/ return err; @@ -578,8 +601,11 @@ int vfsub_trunc(struct path *h_path, loff_t length, unsigned int attr, err = locks_verify_truncate(h_inode, h_file, length); if (!err) err = security_path_truncate(h_path); - if (!err) + if (!err) { + lockdep_off(); err = do_truncate(h_path->dentry, length, attr, h_file); + lockdep_on(); + } out_inode: if (!h_file) @@ -746,7 +772,9 @@ static void call_unlink(void *args) if (h_inode) ihold(h_inode); + lockdep_off(); *a->errp = vfs_unlink(a->dir, d); + lockdep_on(); if (!*a->errp) { struct path tmp = { .dentry = d->d_parent, diff --git a/ubuntu/aufs/vfsub.h b/ubuntu/aufs/vfsub.h index 7615bf02546..486ef20448f 100644 --- a/ubuntu/aufs/vfsub.h +++ b/ubuntu/aufs/vfsub.h @@ -30,8 +30,10 @@ #include "debug.h" /* copied from linux/fs/internal.h */ +/* todo: BAD approach!! */ DECLARE_BRLOCK(vfsmount_lock); extern void file_sb_list_del(struct file *f); +extern spinlock_t inode_sb_list_lock; /* copied from linux/fs/file_table.c */ DECLARE_LGLOCK(files_lglock); @@ -107,6 +109,7 @@ int vfsub_kern_path(const char *name, unsigned int flags, struct path *path); struct dentry *vfsub_lookup_one_len(const char *name, struct dentry *parent, int len); struct dentry *vfsub_lookup_hash(struct nameidata *nd); +int vfsub_name_hash(const char *name, struct qstr *this, int len); /* ---------------------------------------------------------------------- */ @@ -182,7 +185,9 @@ static inline loff_t vfsub_llseek(struct file *file, loff_t offset, int origin) { loff_t err; + lockdep_off(); err = vfs_llseek(file, offset, origin); + lockdep_on(); return err; } diff --git a/ubuntu/aufs/xino.c b/ubuntu/aufs/xino.c index 7c8bb43631a..7c9f521d054 100644 --- a/ubuntu/aufs/xino.c +++ b/ubuntu/aufs/xino.c @@ -169,7 +169,7 @@ struct file *au_xino_create2(struct file *base_file, struct file *copy_src) path.mnt = base_file->f_vfsmnt; file = vfsub_dentry_open(&path, O_RDWR | O_CREAT | O_EXCL | O_LARGEFILE - /* | FMODE_NONOTIFY */); + /* | __FMODE_NONOTIFY */); if (IS_ERR(file)) { pr_err("%.*s open err %ld\n", AuLNPair(name), PTR_ERR(file)); goto out_dput; @@ -686,7 +686,7 @@ struct file *au_xino_create(struct super_block *sb, char *fname, int silent) * when a user specified the xino, we cannot get au_hdir to be ignored. */ file = vfsub_filp_open(fname, O_RDWR | O_CREAT | O_EXCL | O_LARGEFILE - /* | FMODE_NONOTIFY */, + /* | __FMODE_NONOTIFY */, S_IRUGO | S_IWUGO); if (IS_ERR(file)) { if (!silent) diff --git a/ubuntu/include/linux/aufs_type.h b/ubuntu/include/linux/aufs_type.h index 640673bbf00..487a693a213 100644 --- a/ubuntu/include/linux/aufs_type.h +++ b/ubuntu/include/linux/aufs_type.h @@ -24,7 +24,7 @@ #include <linux/limits.h> #include <linux/types.h> -#define AUFS_VERSION "2.1-standalone.tree-38-rcN-20110207" +#define AUFS_VERSION "2.1-standalone.tree-39-rcN-20110418" /* todo? move this to linux-2.6.19/include/magic.h */ #define AUFS_SUPER_MAGIC ('a' << 24 | 'u' << 16 | 'f' << 8 | 's') @@ -118,7 +118,10 @@ enum { AuCtl_RDU_INO, /* pathconf wrapper */ - AuCtl_WBR_FD + AuCtl_WBR_FD, + + /* busy inode */ + AuCtl_IBUSY }; /* borrowed from linux/include/linux/kernel.h */ @@ -189,9 +192,15 @@ struct aufs_rdu { struct au_rdu_cookie cookie; } __aligned(8); +struct aufs_ibusy { + __u64 ino, h_ino; + __s16 bindex; +} __aligned(8); + #define AuCtlType 'A' #define AUFS_CTL_RDU _IOWR(AuCtlType, AuCtl_RDU, struct aufs_rdu) #define AUFS_CTL_RDU_INO _IOWR(AuCtlType, AuCtl_RDU_INO, struct aufs_rdu) #define AUFS_CTL_WBR_FD _IO(AuCtlType, AuCtl_WBR_FD) +#define AUFS_CTL_IBUSY _IOWR(AuCtlType, AuCtl_IBUSY, struct aufs_ibusy) #endif /* __AUFS_TYPE_H__ */ |