aboutsummaryrefslogtreecommitdiffstats
path: root/fs/xfs/xfs_vnodeops.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/xfs/xfs_vnodeops.c')
-rw-r--r--fs/xfs/xfs_vnodeops.c224
1 files changed, 82 insertions, 142 deletions
diff --git a/fs/xfs/xfs_vnodeops.c b/fs/xfs/xfs_vnodeops.c
index 76a1166af822..8b6812f66a15 100644
--- a/fs/xfs/xfs_vnodeops.c
+++ b/fs/xfs/xfs_vnodeops.c
@@ -83,7 +83,7 @@ xfs_setattr(
83 cred_t *credp) 83 cred_t *credp)
84{ 84{
85 xfs_mount_t *mp = ip->i_mount; 85 xfs_mount_t *mp = ip->i_mount;
86 struct inode *inode = XFS_ITOV(ip); 86 struct inode *inode = VFS_I(ip);
87 int mask = iattr->ia_valid; 87 int mask = iattr->ia_valid;
88 xfs_trans_t *tp; 88 xfs_trans_t *tp;
89 int code; 89 int code;
@@ -182,7 +182,7 @@ xfs_setattr(
182 xfs_ilock(ip, lock_flags); 182 xfs_ilock(ip, lock_flags);
183 183
184 /* boolean: are we the file owner? */ 184 /* boolean: are we the file owner? */
185 file_owner = (current_fsuid(credp) == ip->i_d.di_uid); 185 file_owner = (current_fsuid() == ip->i_d.di_uid);
186 186
187 /* 187 /*
188 * Change various properties of a file. 188 * Change various properties of a file.
@@ -513,7 +513,6 @@ xfs_setattr(
513 ip->i_d.di_atime.t_sec = iattr->ia_atime.tv_sec; 513 ip->i_d.di_atime.t_sec = iattr->ia_atime.tv_sec;
514 ip->i_d.di_atime.t_nsec = iattr->ia_atime.tv_nsec; 514 ip->i_d.di_atime.t_nsec = iattr->ia_atime.tv_nsec;
515 ip->i_update_core = 1; 515 ip->i_update_core = 1;
516 timeflags &= ~XFS_ICHGTIME_ACC;
517 } 516 }
518 if (mask & ATTR_MTIME) { 517 if (mask & ATTR_MTIME) {
519 inode->i_mtime = iattr->ia_mtime; 518 inode->i_mtime = iattr->ia_mtime;
@@ -714,7 +713,7 @@ xfs_fsync(
714 return XFS_ERROR(EIO); 713 return XFS_ERROR(EIO);
715 714
716 /* capture size updates in I/O completion before writing the inode. */ 715 /* capture size updates in I/O completion before writing the inode. */
717 error = filemap_fdatawait(vn_to_inode(XFS_ITOV(ip))->i_mapping); 716 error = filemap_fdatawait(VFS_I(ip)->i_mapping);
718 if (error) 717 if (error)
719 return XFS_ERROR(error); 718 return XFS_ERROR(error);
720 719
@@ -1160,7 +1159,6 @@ int
1160xfs_release( 1159xfs_release(
1161 xfs_inode_t *ip) 1160 xfs_inode_t *ip)
1162{ 1161{
1163 bhv_vnode_t *vp = XFS_ITOV(ip);
1164 xfs_mount_t *mp = ip->i_mount; 1162 xfs_mount_t *mp = ip->i_mount;
1165 int error; 1163 int error;
1166 1164
@@ -1195,13 +1193,13 @@ xfs_release(
1195 * be exposed to that problem. 1193 * be exposed to that problem.
1196 */ 1194 */
1197 truncated = xfs_iflags_test_and_clear(ip, XFS_ITRUNCATED); 1195 truncated = xfs_iflags_test_and_clear(ip, XFS_ITRUNCATED);
1198 if (truncated && VN_DIRTY(vp) && ip->i_delayed_blks > 0) 1196 if (truncated && VN_DIRTY(VFS_I(ip)) && ip->i_delayed_blks > 0)
1199 xfs_flush_pages(ip, 0, -1, XFS_B_ASYNC, FI_NONE); 1197 xfs_flush_pages(ip, 0, -1, XFS_B_ASYNC, FI_NONE);
1200 } 1198 }
1201 1199
1202 if (ip->i_d.di_nlink != 0) { 1200 if (ip->i_d.di_nlink != 0) {
1203 if ((((ip->i_d.di_mode & S_IFMT) == S_IFREG) && 1201 if ((((ip->i_d.di_mode & S_IFMT) == S_IFREG) &&
1204 ((ip->i_size > 0) || (VN_CACHED(vp) > 0 || 1202 ((ip->i_size > 0) || (VN_CACHED(VFS_I(ip)) > 0 ||
1205 ip->i_delayed_blks > 0)) && 1203 ip->i_delayed_blks > 0)) &&
1206 (ip->i_df.if_flags & XFS_IFEXTENTS)) && 1204 (ip->i_df.if_flags & XFS_IFEXTENTS)) &&
1207 (!(ip->i_d.di_flags & 1205 (!(ip->i_d.di_flags &
@@ -1227,7 +1225,6 @@ int
1227xfs_inactive( 1225xfs_inactive(
1228 xfs_inode_t *ip) 1226 xfs_inode_t *ip)
1229{ 1227{
1230 bhv_vnode_t *vp = XFS_ITOV(ip);
1231 xfs_bmap_free_t free_list; 1228 xfs_bmap_free_t free_list;
1232 xfs_fsblock_t first_block; 1229 xfs_fsblock_t first_block;
1233 int committed; 1230 int committed;
@@ -1242,7 +1239,7 @@ xfs_inactive(
1242 * If the inode is already free, then there can be nothing 1239 * If the inode is already free, then there can be nothing
1243 * to clean up here. 1240 * to clean up here.
1244 */ 1241 */
1245 if (ip->i_d.di_mode == 0 || VN_BAD(vp)) { 1242 if (ip->i_d.di_mode == 0 || VN_BAD(VFS_I(ip))) {
1246 ASSERT(ip->i_df.if_real_bytes == 0); 1243 ASSERT(ip->i_df.if_real_bytes == 0);
1247 ASSERT(ip->i_df.if_broot_bytes == 0); 1244 ASSERT(ip->i_df.if_broot_bytes == 0);
1248 return VN_INACTIVE_CACHE; 1245 return VN_INACTIVE_CACHE;
@@ -1272,7 +1269,7 @@ xfs_inactive(
1272 1269
1273 if (ip->i_d.di_nlink != 0) { 1270 if (ip->i_d.di_nlink != 0) {
1274 if ((((ip->i_d.di_mode & S_IFMT) == S_IFREG) && 1271 if ((((ip->i_d.di_mode & S_IFMT) == S_IFREG) &&
1275 ((ip->i_size > 0) || (VN_CACHED(vp) > 0 || 1272 ((ip->i_size > 0) || (VN_CACHED(VFS_I(ip)) > 0 ||
1276 ip->i_delayed_blks > 0)) && 1273 ip->i_delayed_blks > 0)) &&
1277 (ip->i_df.if_flags & XFS_IFEXTENTS) && 1274 (ip->i_df.if_flags & XFS_IFEXTENTS) &&
1278 (!(ip->i_d.di_flags & 1275 (!(ip->i_d.di_flags &
@@ -1536,7 +1533,7 @@ xfs_create(
1536 * Make sure that we have allocated dquot(s) on disk. 1533 * Make sure that we have allocated dquot(s) on disk.
1537 */ 1534 */
1538 error = XFS_QM_DQVOPALLOC(mp, dp, 1535 error = XFS_QM_DQVOPALLOC(mp, dp,
1539 current_fsuid(credp), current_fsgid(credp), prid, 1536 current_fsuid(), current_fsgid(), prid,
1540 XFS_QMOPT_QUOTALL|XFS_QMOPT_INHERIT, &udqp, &gdqp); 1537 XFS_QMOPT_QUOTALL|XFS_QMOPT_INHERIT, &udqp, &gdqp);
1541 if (error) 1538 if (error)
1542 goto std_return; 1539 goto std_return;
@@ -1708,111 +1705,6 @@ std_return:
1708} 1705}
1709 1706
1710#ifdef DEBUG 1707#ifdef DEBUG
1711/*
1712 * Some counters to see if (and how often) we are hitting some deadlock
1713 * prevention code paths.
1714 */
1715
1716int xfs_rm_locks;
1717int xfs_rm_lock_delays;
1718int xfs_rm_attempts;
1719#endif
1720
1721/*
1722 * The following routine will lock the inodes associated with the
1723 * directory and the named entry in the directory. The locks are
1724 * acquired in increasing inode number.
1725 *
1726 * If the entry is "..", then only the directory is locked. The
1727 * vnode ref count will still include that from the .. entry in
1728 * this case.
1729 *
1730 * There is a deadlock we need to worry about. If the locked directory is
1731 * in the AIL, it might be blocking up the log. The next inode we lock
1732 * could be already locked by another thread waiting for log space (e.g
1733 * a permanent log reservation with a long running transaction (see
1734 * xfs_itruncate_finish)). To solve this, we must check if the directory
1735 * is in the ail and use lock_nowait. If we can't lock, we need to
1736 * drop the inode lock on the directory and try again. xfs_iunlock will
1737 * potentially push the tail if we were holding up the log.
1738 */
1739STATIC int
1740xfs_lock_dir_and_entry(
1741 xfs_inode_t *dp,
1742 xfs_inode_t *ip) /* inode of entry 'name' */
1743{
1744 int attempts;
1745 xfs_ino_t e_inum;
1746 xfs_inode_t *ips[2];
1747 xfs_log_item_t *lp;
1748
1749#ifdef DEBUG
1750 xfs_rm_locks++;
1751#endif
1752 attempts = 0;
1753
1754again:
1755 xfs_ilock(dp, XFS_ILOCK_EXCL | XFS_ILOCK_PARENT);
1756
1757 e_inum = ip->i_ino;
1758
1759 xfs_itrace_ref(ip);
1760
1761 /*
1762 * We want to lock in increasing inum. Since we've already
1763 * acquired the lock on the directory, we may need to release
1764 * if if the inum of the entry turns out to be less.
1765 */
1766 if (e_inum > dp->i_ino) {
1767 /*
1768 * We are already in the right order, so just
1769 * lock on the inode of the entry.
1770 * We need to use nowait if dp is in the AIL.
1771 */
1772
1773 lp = (xfs_log_item_t *)dp->i_itemp;
1774 if (lp && (lp->li_flags & XFS_LI_IN_AIL)) {
1775 if (!xfs_ilock_nowait(ip, XFS_ILOCK_EXCL)) {
1776 attempts++;
1777#ifdef DEBUG
1778 xfs_rm_attempts++;
1779#endif
1780
1781 /*
1782 * Unlock dp and try again.
1783 * xfs_iunlock will try to push the tail
1784 * if the inode is in the AIL.
1785 */
1786
1787 xfs_iunlock(dp, XFS_ILOCK_EXCL);
1788
1789 if ((attempts % 5) == 0) {
1790 delay(1); /* Don't just spin the CPU */
1791#ifdef DEBUG
1792 xfs_rm_lock_delays++;
1793#endif
1794 }
1795 goto again;
1796 }
1797 } else {
1798 xfs_ilock(ip, XFS_ILOCK_EXCL);
1799 }
1800 } else if (e_inum < dp->i_ino) {
1801 xfs_iunlock(dp, XFS_ILOCK_EXCL);
1802
1803 ips[0] = ip;
1804 ips[1] = dp;
1805 xfs_lock_inodes(ips, 2, XFS_ILOCK_EXCL);
1806 }
1807 /* else e_inum == dp->i_ino */
1808 /* This can happen if we're asked to lock /x/..
1809 * the entry is "..", which is also the parent directory.
1810 */
1811
1812 return 0;
1813}
1814
1815#ifdef DEBUG
1816int xfs_locked_n; 1708int xfs_locked_n;
1817int xfs_small_retries; 1709int xfs_small_retries;
1818int xfs_middle_retries; 1710int xfs_middle_retries;
@@ -1946,6 +1838,53 @@ again:
1946#endif 1838#endif
1947} 1839}
1948 1840
1841/*
1842 * xfs_lock_two_inodes() can only be used to lock one type of lock
1843 * at a time - the iolock or the ilock, but not both at once. If
1844 * we lock both at once, lockdep will report false positives saying
1845 * we have violated locking orders.
1846 */
1847void
1848xfs_lock_two_inodes(
1849 xfs_inode_t *ip0,
1850 xfs_inode_t *ip1,
1851 uint lock_mode)
1852{
1853 xfs_inode_t *temp;
1854 int attempts = 0;
1855 xfs_log_item_t *lp;
1856
1857 if (lock_mode & (XFS_IOLOCK_SHARED|XFS_IOLOCK_EXCL))
1858 ASSERT((lock_mode & (XFS_ILOCK_SHARED|XFS_ILOCK_EXCL)) == 0);
1859 ASSERT(ip0->i_ino != ip1->i_ino);
1860
1861 if (ip0->i_ino > ip1->i_ino) {
1862 temp = ip0;
1863 ip0 = ip1;
1864 ip1 = temp;
1865 }
1866
1867 again:
1868 xfs_ilock(ip0, xfs_lock_inumorder(lock_mode, 0));
1869
1870 /*
1871 * If the first lock we have locked is in the AIL, we must TRY to get
1872 * the second lock. If we can't get it, we must release the first one
1873 * and try again.
1874 */
1875 lp = (xfs_log_item_t *)ip0->i_itemp;
1876 if (lp && (lp->li_flags & XFS_LI_IN_AIL)) {
1877 if (!xfs_ilock_nowait(ip1, xfs_lock_inumorder(lock_mode, 1))) {
1878 xfs_iunlock(ip0, lock_mode);
1879 if ((++attempts % 5) == 0)
1880 delay(1); /* Don't just spin the CPU */
1881 goto again;
1882 }
1883 } else {
1884 xfs_ilock(ip1, xfs_lock_inumorder(lock_mode, 1));
1885 }
1886}
1887
1949int 1888int
1950xfs_remove( 1889xfs_remove(
1951 xfs_inode_t *dp, 1890 xfs_inode_t *dp,
@@ -2018,9 +1957,7 @@ xfs_remove(
2018 goto out_trans_cancel; 1957 goto out_trans_cancel;
2019 } 1958 }
2020 1959
2021 error = xfs_lock_dir_and_entry(dp, ip); 1960 xfs_lock_two_inodes(dp, ip, XFS_ILOCK_EXCL);
2022 if (error)
2023 goto out_trans_cancel;
2024 1961
2025 /* 1962 /*
2026 * At this point, we've gotten both the directory and the entry 1963 * At this point, we've gotten both the directory and the entry
@@ -2047,9 +1984,6 @@ xfs_remove(
2047 } 1984 }
2048 } 1985 }
2049 1986
2050 /*
2051 * Entry must exist since we did a lookup in xfs_lock_dir_and_entry.
2052 */
2053 XFS_BMAP_INIT(&free_list, &first_block); 1987 XFS_BMAP_INIT(&free_list, &first_block);
2054 error = xfs_dir_removename(tp, dp, name, ip->i_ino, 1988 error = xfs_dir_removename(tp, dp, name, ip->i_ino,
2055 &first_block, &free_list, resblks); 1989 &first_block, &free_list, resblks);
@@ -2155,7 +2089,6 @@ xfs_link(
2155{ 2089{
2156 xfs_mount_t *mp = tdp->i_mount; 2090 xfs_mount_t *mp = tdp->i_mount;
2157 xfs_trans_t *tp; 2091 xfs_trans_t *tp;
2158 xfs_inode_t *ips[2];
2159 int error; 2092 int error;
2160 xfs_bmap_free_t free_list; 2093 xfs_bmap_free_t free_list;
2161 xfs_fsblock_t first_block; 2094 xfs_fsblock_t first_block;
@@ -2203,15 +2136,7 @@ xfs_link(
2203 goto error_return; 2136 goto error_return;
2204 } 2137 }
2205 2138
2206 if (sip->i_ino < tdp->i_ino) { 2139 xfs_lock_two_inodes(sip, tdp, XFS_ILOCK_EXCL);
2207 ips[0] = sip;
2208 ips[1] = tdp;
2209 } else {
2210 ips[0] = tdp;
2211 ips[1] = sip;
2212 }
2213
2214 xfs_lock_inodes(ips, 2, XFS_ILOCK_EXCL);
2215 2140
2216 /* 2141 /*
2217 * Increment vnode ref counts since xfs_trans_commit & 2142 * Increment vnode ref counts since xfs_trans_commit &
@@ -2352,7 +2277,7 @@ xfs_mkdir(
2352 * Make sure that we have allocated dquot(s) on disk. 2277 * Make sure that we have allocated dquot(s) on disk.
2353 */ 2278 */
2354 error = XFS_QM_DQVOPALLOC(mp, dp, 2279 error = XFS_QM_DQVOPALLOC(mp, dp,
2355 current_fsuid(credp), current_fsgid(credp), prid, 2280 current_fsuid(), current_fsgid(), prid,
2356 XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp); 2281 XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp);
2357 if (error) 2282 if (error)
2358 goto std_return; 2283 goto std_return;
@@ -2578,7 +2503,7 @@ xfs_symlink(
2578 * Make sure that we have allocated dquot(s) on disk. 2503 * Make sure that we have allocated dquot(s) on disk.
2579 */ 2504 */
2580 error = XFS_QM_DQVOPALLOC(mp, dp, 2505 error = XFS_QM_DQVOPALLOC(mp, dp,
2581 current_fsuid(credp), current_fsgid(credp), prid, 2506 current_fsuid(), current_fsgid(), prid,
2582 XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp); 2507 XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT, &udqp, &gdqp);
2583 if (error) 2508 if (error)
2584 goto std_return; 2509 goto std_return;
@@ -2873,14 +2798,13 @@ int
2873xfs_reclaim( 2798xfs_reclaim(
2874 xfs_inode_t *ip) 2799 xfs_inode_t *ip)
2875{ 2800{
2876 bhv_vnode_t *vp = XFS_ITOV(ip);
2877 2801
2878 xfs_itrace_entry(ip); 2802 xfs_itrace_entry(ip);
2879 2803
2880 ASSERT(!VN_MAPPED(vp)); 2804 ASSERT(!VN_MAPPED(VFS_I(ip)));
2881 2805
2882 /* bad inode, get out here ASAP */ 2806 /* bad inode, get out here ASAP */
2883 if (VN_BAD(vp)) { 2807 if (VN_BAD(VFS_I(ip))) {
2884 xfs_ireclaim(ip); 2808 xfs_ireclaim(ip);
2885 return 0; 2809 return 0;
2886 } 2810 }
@@ -2917,7 +2841,7 @@ xfs_reclaim(
2917 XFS_MOUNT_ILOCK(mp); 2841 XFS_MOUNT_ILOCK(mp);
2918 spin_lock(&ip->i_flags_lock); 2842 spin_lock(&ip->i_flags_lock);
2919 __xfs_iflags_set(ip, XFS_IRECLAIMABLE); 2843 __xfs_iflags_set(ip, XFS_IRECLAIMABLE);
2920 vn_to_inode(vp)->i_private = NULL; 2844 VFS_I(ip)->i_private = NULL;
2921 ip->i_vnode = NULL; 2845 ip->i_vnode = NULL;
2922 spin_unlock(&ip->i_flags_lock); 2846 spin_unlock(&ip->i_flags_lock);
2923 list_add_tail(&ip->i_reclaim, &mp->m_del_inodes); 2847 list_add_tail(&ip->i_reclaim, &mp->m_del_inodes);
@@ -2933,7 +2857,7 @@ xfs_finish_reclaim(
2933 int sync_mode) 2857 int sync_mode)
2934{ 2858{
2935 xfs_perag_t *pag = xfs_get_perag(ip->i_mount, ip->i_ino); 2859 xfs_perag_t *pag = xfs_get_perag(ip->i_mount, ip->i_ino);
2936 bhv_vnode_t *vp = XFS_ITOV_NULL(ip); 2860 struct inode *vp = VFS_I(ip);
2937 2861
2938 if (vp && VN_BAD(vp)) 2862 if (vp && VN_BAD(vp))
2939 goto reclaim; 2863 goto reclaim;
@@ -3236,6 +3160,13 @@ error1: /* Just cancel transaction */
3236/* 3160/*
3237 * Zero file bytes between startoff and endoff inclusive. 3161 * Zero file bytes between startoff and endoff inclusive.
3238 * The iolock is held exclusive and no blocks are buffered. 3162 * The iolock is held exclusive and no blocks are buffered.
3163 *
3164 * This function is used by xfs_free_file_space() to zero
3165 * partial blocks when the range to free is not block aligned.
3166 * When unreserving space with boundaries that are not block
3167 * aligned we round up the start and round down the end
3168 * boundaries and then use this function to zero the parts of
3169 * the blocks that got dropped during the rounding.
3239 */ 3170 */
3240STATIC int 3171STATIC int
3241xfs_zero_remaining_bytes( 3172xfs_zero_remaining_bytes(
@@ -3252,6 +3183,17 @@ xfs_zero_remaining_bytes(
3252 int nimap; 3183 int nimap;
3253 int error = 0; 3184 int error = 0;
3254 3185
3186 /*
3187 * Avoid doing I/O beyond eof - it's not necessary
3188 * since nothing can read beyond eof. The space will
3189 * be zeroed when the file is extended anyway.
3190 */
3191 if (startoff >= ip->i_size)
3192 return 0;
3193
3194 if (endoff > ip->i_size)
3195 endoff = ip->i_size;
3196
3255 bp = xfs_buf_get_noaddr(mp->m_sb.sb_blocksize, 3197 bp = xfs_buf_get_noaddr(mp->m_sb.sb_blocksize,
3256 XFS_IS_REALTIME_INODE(ip) ? 3198 XFS_IS_REALTIME_INODE(ip) ?
3257 mp->m_rtdev_targp : mp->m_ddev_targp); 3199 mp->m_rtdev_targp : mp->m_ddev_targp);
@@ -3321,7 +3263,6 @@ xfs_free_file_space(
3321 xfs_off_t len, 3263 xfs_off_t len,
3322 int attr_flags) 3264 int attr_flags)
3323{ 3265{
3324 bhv_vnode_t *vp;
3325 int committed; 3266 int committed;
3326 int done; 3267 int done;
3327 xfs_off_t end_dmi_offset; 3268 xfs_off_t end_dmi_offset;
@@ -3341,7 +3282,6 @@ xfs_free_file_space(
3341 xfs_trans_t *tp; 3282 xfs_trans_t *tp;
3342 int need_iolock = 1; 3283 int need_iolock = 1;
3343 3284
3344 vp = XFS_ITOV(ip);
3345 mp = ip->i_mount; 3285 mp = ip->i_mount;
3346 3286
3347 xfs_itrace_entry(ip); 3287 xfs_itrace_entry(ip);
@@ -3378,7 +3318,7 @@ xfs_free_file_space(
3378 rounding = max_t(uint, 1 << mp->m_sb.sb_blocklog, PAGE_CACHE_SIZE); 3318 rounding = max_t(uint, 1 << mp->m_sb.sb_blocklog, PAGE_CACHE_SIZE);
3379 ioffset = offset & ~(rounding - 1); 3319 ioffset = offset & ~(rounding - 1);
3380 3320
3381 if (VN_CACHED(vp) != 0) { 3321 if (VN_CACHED(VFS_I(ip)) != 0) {
3382 xfs_inval_cached_trace(ip, ioffset, -1, ioffset, -1); 3322 xfs_inval_cached_trace(ip, ioffset, -1, ioffset, -1);
3383 error = xfs_flushinval_pages(ip, ioffset, -1, FI_REMAPF_LOCKED); 3323 error = xfs_flushinval_pages(ip, ioffset, -1, FI_REMAPF_LOCKED);
3384 if (error) 3324 if (error)