aboutsummaryrefslogtreecommitdiffstats
path: root/fs/xfs/xfs_alloc.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/xfs/xfs_alloc.c')
-rw-r--r--fs/xfs/xfs_alloc.c113
1 files changed, 60 insertions, 53 deletions
diff --git a/fs/xfs/xfs_alloc.c b/fs/xfs/xfs_alloc.c
index eef6763f3a67..e80dda3437d1 100644
--- a/fs/xfs/xfs_alloc.c
+++ b/fs/xfs/xfs_alloc.c
@@ -1477,8 +1477,10 @@ xfs_alloc_ag_vextent_small(
1477 /* 1477 /*
1478 * Can't allocate from the freelist for some reason. 1478 * Can't allocate from the freelist for some reason.
1479 */ 1479 */
1480 else 1480 else {
1481 fbno = NULLAGBLOCK;
1481 flen = 0; 1482 flen = 0;
1483 }
1482 /* 1484 /*
1483 * Can't do the allocation, give up. 1485 * Can't do the allocation, give up.
1484 */ 1486 */
@@ -1835,40 +1837,47 @@ xfs_alloc_fix_freelist(
1835 &agbp))) 1837 &agbp)))
1836 return error; 1838 return error;
1837 if (!pag->pagf_init) { 1839 if (!pag->pagf_init) {
1840 ASSERT(flags & XFS_ALLOC_FLAG_TRYLOCK);
1841 ASSERT(!(flags & XFS_ALLOC_FLAG_FREEING));
1838 args->agbp = NULL; 1842 args->agbp = NULL;
1839 return 0; 1843 return 0;
1840 } 1844 }
1841 } else 1845 } else
1842 agbp = NULL; 1846 agbp = NULL;
1843 1847
1844 /* If this is a metadata preferred pag and we are user data 1848 /*
1849 * If this is a metadata preferred pag and we are user data
1845 * then try somewhere else if we are not being asked to 1850 * then try somewhere else if we are not being asked to
1846 * try harder at this point 1851 * try harder at this point
1847 */ 1852 */
1848 if (pag->pagf_metadata && args->userdata && flags) { 1853 if (pag->pagf_metadata && args->userdata &&
1854 (flags & XFS_ALLOC_FLAG_TRYLOCK)) {
1855 ASSERT(!(flags & XFS_ALLOC_FLAG_FREEING));
1849 args->agbp = NULL; 1856 args->agbp = NULL;
1850 return 0; 1857 return 0;
1851 } 1858 }
1852 1859
1853 need = XFS_MIN_FREELIST_PAG(pag, mp); 1860 if (!(flags & XFS_ALLOC_FLAG_FREEING)) {
1854 delta = need > pag->pagf_flcount ? need - pag->pagf_flcount : 0; 1861 need = XFS_MIN_FREELIST_PAG(pag, mp);
1855 /* 1862 delta = need > pag->pagf_flcount ? need - pag->pagf_flcount : 0;
1856 * If it looks like there isn't a long enough extent, or enough 1863 /*
1857 * total blocks, reject it. 1864 * If it looks like there isn't a long enough extent, or enough
1858 */ 1865 * total blocks, reject it.
1859 longest = (pag->pagf_longest > delta) ? 1866 */
1860 (pag->pagf_longest - delta) : 1867 longest = (pag->pagf_longest > delta) ?
1861 (pag->pagf_flcount > 0 || pag->pagf_longest > 0); 1868 (pag->pagf_longest - delta) :
1862 if (args->minlen + args->alignment + args->minalignslop - 1 > longest || 1869 (pag->pagf_flcount > 0 || pag->pagf_longest > 0);
1863 (!(flags & XFS_ALLOC_FLAG_FREEING) && 1870 if ((args->minlen + args->alignment + args->minalignslop - 1) >
1864 (int)(pag->pagf_freeblks + pag->pagf_flcount - 1871 longest ||
1865 need - args->total) < 1872 ((int)(pag->pagf_freeblks + pag->pagf_flcount -
1866 (int)args->minleft)) { 1873 need - args->total) < (int)args->minleft)) {
1867 if (agbp) 1874 if (agbp)
1868 xfs_trans_brelse(tp, agbp); 1875 xfs_trans_brelse(tp, agbp);
1869 args->agbp = NULL; 1876 args->agbp = NULL;
1870 return 0; 1877 return 0;
1878 }
1871 } 1879 }
1880
1872 /* 1881 /*
1873 * Get the a.g. freespace buffer. 1882 * Get the a.g. freespace buffer.
1874 * Can fail if we're not blocking on locks, and it's held. 1883 * Can fail if we're not blocking on locks, and it's held.
@@ -1878,6 +1887,8 @@ xfs_alloc_fix_freelist(
1878 &agbp))) 1887 &agbp)))
1879 return error; 1888 return error;
1880 if (agbp == NULL) { 1889 if (agbp == NULL) {
1890 ASSERT(flags & XFS_ALLOC_FLAG_TRYLOCK);
1891 ASSERT(!(flags & XFS_ALLOC_FLAG_FREEING));
1881 args->agbp = NULL; 1892 args->agbp = NULL;
1882 return 0; 1893 return 0;
1883 } 1894 }
@@ -1887,22 +1898,24 @@ xfs_alloc_fix_freelist(
1887 */ 1898 */
1888 agf = XFS_BUF_TO_AGF(agbp); 1899 agf = XFS_BUF_TO_AGF(agbp);
1889 need = XFS_MIN_FREELIST(agf, mp); 1900 need = XFS_MIN_FREELIST(agf, mp);
1890 delta = need > be32_to_cpu(agf->agf_flcount) ?
1891 (need - be32_to_cpu(agf->agf_flcount)) : 0;
1892 /* 1901 /*
1893 * If there isn't enough total or single-extent, reject it. 1902 * If there isn't enough total or single-extent, reject it.
1894 */ 1903 */
1895 longest = be32_to_cpu(agf->agf_longest); 1904 if (!(flags & XFS_ALLOC_FLAG_FREEING)) {
1896 longest = (longest > delta) ? (longest - delta) : 1905 delta = need > be32_to_cpu(agf->agf_flcount) ?
1897 (be32_to_cpu(agf->agf_flcount) > 0 || longest > 0); 1906 (need - be32_to_cpu(agf->agf_flcount)) : 0;
1898 if (args->minlen + args->alignment + args->minalignslop - 1 > longest || 1907 longest = be32_to_cpu(agf->agf_longest);
1899 (!(flags & XFS_ALLOC_FLAG_FREEING) && 1908 longest = (longest > delta) ? (longest - delta) :
1900 (int)(be32_to_cpu(agf->agf_freeblks) + 1909 (be32_to_cpu(agf->agf_flcount) > 0 || longest > 0);
1901 be32_to_cpu(agf->agf_flcount) - need - args->total) < 1910 if ((args->minlen + args->alignment + args->minalignslop - 1) >
1902 (int)args->minleft)) { 1911 longest ||
1903 xfs_trans_brelse(tp, agbp); 1912 ((int)(be32_to_cpu(agf->agf_freeblks) +
1904 args->agbp = NULL; 1913 be32_to_cpu(agf->agf_flcount) - need - args->total) <
1905 return 0; 1914 (int)args->minleft)) {
1915 xfs_trans_brelse(tp, agbp);
1916 args->agbp = NULL;
1917 return 0;
1918 }
1906 } 1919 }
1907 /* 1920 /*
1908 * Make the freelist shorter if it's too long. 1921 * Make the freelist shorter if it's too long.
@@ -1950,12 +1963,11 @@ xfs_alloc_fix_freelist(
1950 * on a completely full ag. 1963 * on a completely full ag.
1951 */ 1964 */
1952 if (targs.agbno == NULLAGBLOCK) { 1965 if (targs.agbno == NULLAGBLOCK) {
1953 if (!(flags & XFS_ALLOC_FLAG_FREEING)) { 1966 if (flags & XFS_ALLOC_FLAG_FREEING)
1954 xfs_trans_brelse(tp, agflbp); 1967 break;
1955 args->agbp = NULL; 1968 xfs_trans_brelse(tp, agflbp);
1956 return 0; 1969 args->agbp = NULL;
1957 } 1970 return 0;
1958 break;
1959 } 1971 }
1960 /* 1972 /*
1961 * Put each allocated block on the list. 1973 * Put each allocated block on the list.
@@ -2011,7 +2023,7 @@ xfs_alloc_get_freelist(
2011 /* 2023 /*
2012 * Get the block number and update the data structures. 2024 * Get the block number and update the data structures.
2013 */ 2025 */
2014 bno = INT_GET(agfl->agfl_bno[be32_to_cpu(agf->agf_flfirst)], ARCH_CONVERT); 2026 bno = be32_to_cpu(agfl->agfl_bno[be32_to_cpu(agf->agf_flfirst)]);
2015 be32_add(&agf->agf_flfirst, 1); 2027 be32_add(&agf->agf_flfirst, 1);
2016 xfs_trans_brelse(tp, agflbp); 2028 xfs_trans_brelse(tp, agflbp);
2017 if (be32_to_cpu(agf->agf_flfirst) == XFS_AGFL_SIZE(mp)) 2029 if (be32_to_cpu(agf->agf_flfirst) == XFS_AGFL_SIZE(mp))
@@ -2098,7 +2110,7 @@ xfs_alloc_put_freelist(
2098{ 2110{
2099 xfs_agf_t *agf; /* a.g. freespace structure */ 2111 xfs_agf_t *agf; /* a.g. freespace structure */
2100 xfs_agfl_t *agfl; /* a.g. free block array */ 2112 xfs_agfl_t *agfl; /* a.g. free block array */
2101 xfs_agblock_t *blockp;/* pointer to array entry */ 2113 __be32 *blockp;/* pointer to array entry */
2102 int error; 2114 int error;
2103#ifdef XFS_ALLOC_TRACE 2115#ifdef XFS_ALLOC_TRACE
2104 static char fname[] = "xfs_alloc_put_freelist"; 2116 static char fname[] = "xfs_alloc_put_freelist";
@@ -2122,7 +2134,7 @@ xfs_alloc_put_freelist(
2122 pag->pagf_flcount++; 2134 pag->pagf_flcount++;
2123 ASSERT(be32_to_cpu(agf->agf_flcount) <= XFS_AGFL_SIZE(mp)); 2135 ASSERT(be32_to_cpu(agf->agf_flcount) <= XFS_AGFL_SIZE(mp));
2124 blockp = &agfl->agfl_bno[be32_to_cpu(agf->agf_fllast)]; 2136 blockp = &agfl->agfl_bno[be32_to_cpu(agf->agf_fllast)];
2125 INT_SET(*blockp, ARCH_CONVERT, bno); 2137 *blockp = cpu_to_be32(bno);
2126 TRACE_MODAGF(NULL, agf, XFS_AGF_FLLAST | XFS_AGF_FLCOUNT); 2138 TRACE_MODAGF(NULL, agf, XFS_AGF_FLLAST | XFS_AGF_FLCOUNT);
2127 xfs_alloc_log_agf(tp, agbp, XFS_AGF_FLLAST | XFS_AGF_FLCOUNT); 2139 xfs_alloc_log_agf(tp, agbp, XFS_AGF_FLLAST | XFS_AGF_FLCOUNT);
2128 xfs_trans_log_buf(tp, agflbp, 2140 xfs_trans_log_buf(tp, agflbp,
@@ -2442,31 +2454,26 @@ xfs_free_extent(
2442 xfs_fsblock_t bno, /* starting block number of extent */ 2454 xfs_fsblock_t bno, /* starting block number of extent */
2443 xfs_extlen_t len) /* length of extent */ 2455 xfs_extlen_t len) /* length of extent */
2444{ 2456{
2445#ifdef DEBUG 2457 xfs_alloc_arg_t args;
2446 xfs_agf_t *agf; /* a.g. freespace header */
2447#endif
2448 xfs_alloc_arg_t args; /* allocation argument structure */
2449 int error; 2458 int error;
2450 2459
2451 ASSERT(len != 0); 2460 ASSERT(len != 0);
2461 memset(&args, 0, sizeof(xfs_alloc_arg_t));
2452 args.tp = tp; 2462 args.tp = tp;
2453 args.mp = tp->t_mountp; 2463 args.mp = tp->t_mountp;
2454 args.agno = XFS_FSB_TO_AGNO(args.mp, bno); 2464 args.agno = XFS_FSB_TO_AGNO(args.mp, bno);
2455 ASSERT(args.agno < args.mp->m_sb.sb_agcount); 2465 ASSERT(args.agno < args.mp->m_sb.sb_agcount);
2456 args.agbno = XFS_FSB_TO_AGBNO(args.mp, bno); 2466 args.agbno = XFS_FSB_TO_AGBNO(args.mp, bno);
2457 args.alignment = 1;
2458 args.minlen = args.minleft = args.minalignslop = 0;
2459 down_read(&args.mp->m_peraglock); 2467 down_read(&args.mp->m_peraglock);
2460 args.pag = &args.mp->m_perag[args.agno]; 2468 args.pag = &args.mp->m_perag[args.agno];
2461 if ((error = xfs_alloc_fix_freelist(&args, XFS_ALLOC_FLAG_FREEING))) 2469 if ((error = xfs_alloc_fix_freelist(&args, XFS_ALLOC_FLAG_FREEING)))
2462 goto error0; 2470 goto error0;
2463#ifdef DEBUG 2471#ifdef DEBUG
2464 ASSERT(args.agbp != NULL); 2472 ASSERT(args.agbp != NULL);
2465 agf = XFS_BUF_TO_AGF(args.agbp); 2473 ASSERT((args.agbno + len) <=
2466 ASSERT(args.agbno + len <= be32_to_cpu(agf->agf_length)); 2474 be32_to_cpu(XFS_BUF_TO_AGF(args.agbp)->agf_length));
2467#endif 2475#endif
2468 error = xfs_free_ag_extent(tp, args.agbp, args.agno, args.agbno, 2476 error = xfs_free_ag_extent(tp, args.agbp, args.agno, args.agbno, len, 0);
2469 len, 0);
2470error0: 2477error0:
2471 up_read(&args.mp->m_peraglock); 2478 up_read(&args.mp->m_peraglock);
2472 return error; 2479 return error;