Link Here
|
792 |
} |
879 |
} |
793 |
|
880 |
|
794 |
/* |
881 |
/* |
|
|
882 |
* SWP_FIND_CONTINUOUS_REGION() - find a continuous region of swap blocks |
883 |
* |
884 |
* Given the "start" entry is not SWAPBLK_NONE, it searches a range |
885 |
* if SWAPBLK to be up to including "last" element. |
886 |
* |
887 |
* The return value indicates the number of blocks freed. |
888 |
* |
889 |
* An example of good case is when swblk holds [2, 3, 4, 5, 6, 7, 8, 9], |
890 |
* caller passes (&d[0], and &[7]) as arguments and 8 is returned. |
891 |
* |
892 |
* Another example is with [NONE, 3, NONE, 11, 12, 13, 4, NONE], |
893 |
* caller wants to skip d[0] and passes (&d[1], &d[7]) which |
894 |
* returns 1 block. Then, caller skips d[2] and pass (&d[3], &d[7]) which |
895 |
* returns 3 blocks as 4 is not a number fater 13 and not continous. |
896 |
* Then callers get 1 block back for &d[6] and won't want to call |
897 |
* for &d[7] as it is NONE. |
898 |
*/ |
899 |
static int |
900 |
swp_find_continuous_region(const daddr_t *start, const daddr_t *last) |
901 |
{ |
902 |
const daddr_t *next; |
903 |
daddr_t expected; |
904 |
|
905 |
if (*start == SWAPBLK_NONE) |
906 |
return 0; |
907 |
|
908 |
next = start + 1; |
909 |
expected = *start + 1; |
910 |
while (next <= last && (expected == *next)) |
911 |
{ |
912 |
next++; |
913 |
expected++; |
914 |
} |
915 |
return npages = next - start; |
916 |
} |
917 |
|
918 |
/* |
795 |
* SYSCTL_SWAP_FRAGMENTATION() - produce raw swap space stats |
919 |
* SYSCTL_SWAP_FRAGMENTATION() - produce raw swap space stats |
796 |
*/ |
920 |
*/ |
797 |
static int |
921 |
static int |
Link Here
|
1888 |
static void |
2047 |
static void |
1889 |
swp_pager_meta_free(vm_object_t object, vm_pindex_t pindex, vm_pindex_t count) |
2048 |
swp_pager_meta_free(vm_object_t object, vm_pindex_t pindex, vm_pindex_t count) |
1890 |
{ |
2049 |
{ |
|
|
2050 |
int offset, npages; |
1891 |
struct swblk *sb; |
2051 |
struct swblk *sb; |
1892 |
vm_pindex_t last; |
2052 |
vm_pindex_t last; |
1893 |
int i; |
2053 |
int i; |
Link Here
|
1908 |
if (sb->d[i] == SWAPBLK_NONE) |
2072 |
if (sb->d[i] == SWAPBLK_NONE) |
1909 |
continue; |
2073 |
continue; |
1910 |
if (pindex <= sb->p + i && sb->p + i <= last) { |
2074 |
if (pindex <= sb->p + i && sb->p + i <= last) { |
1911 |
swp_pager_freeswapspace(sb->d[i], 1); |
2075 |
offset = last - (sb->p + i); |
|
|
2076 |
if (offset == 0) { |
2077 |
npages = 1; |
2078 |
} else { |
2079 |
offset = min(offset, (SWAP_META_PAGES - 1 - i)); |
2080 |
npages = swp_find_continuous_region(&sb->d[i], &sb->d[i + offset]); |
2081 |
printf("swp_find_continuous_region:start %lld@d[%d] offset=%d %lld->%d\n", |
2082 |
sb->d[i], i, offset, sb->d[i], npages); |
2083 |
} |
2084 |
swp_pager_freeswapspace(sb->d[i], npages); |
2085 |
while( npages-- > 1 ) |
2086 |
sb->d[i++] = SWAPBLK_NONE; |
1912 |
sb->d[i] = SWAPBLK_NONE; |
2087 |
sb->d[i] = SWAPBLK_NONE; |
1913 |
} else |
2088 |
} else |
1914 |
empty = false; |
2089 |
empty = false; |
Link Here
|
1933 |
{ |
2108 |
{ |
1934 |
struct swblk *sb; |
2109 |
struct swblk *sb; |
1935 |
vm_pindex_t pindex; |
2110 |
vm_pindex_t pindex; |
1936 |
int i; |
2111 |
int i, npages; |
1937 |
|
2112 |
|
1938 |
VM_OBJECT_ASSERT_WLOCKED(object); |
2113 |
VM_OBJECT_ASSERT_WLOCKED(object); |
1939 |
if (object->type != OBJT_SWAP) |
2114 |
if (object->type != OBJT_SWAP) |
Link Here
|
1942 |
for (pindex = 0; (sb = SWAP_PCTRIE_LOOKUP_GE( |
2117 |
for (pindex = 0; (sb = SWAP_PCTRIE_LOOKUP_GE( |
1943 |
&object->un_pager.swp.swp_blks, pindex)) != NULL;) { |
2118 |
&object->un_pager.swp.swp_blks, pindex)) != NULL;) { |
1944 |
pindex = sb->p + SWAP_META_PAGES; |
2119 |
pindex = sb->p + SWAP_META_PAGES; |
1945 |
for (i = 0; i < SWAP_META_PAGES; i++) { |
2120 |
for (i = 0; i < SWAP_META_PAGES;) { |
1946 |
if (sb->d[i] != SWAPBLK_NONE) |
2121 |
if (sb->d[i] != SWAPBLK_NONE) { |
1947 |
swp_pager_freeswapspace(sb->d[i], 1); |
2122 |
npages = swp_find_continuous_region(&sb->d[i], &sb->d[SWAP_META_PAGES - 1]); |
|
|
2123 |
swp_pager_freeswapspace(sb->d[i], npages); |
2124 |
i += npages; |
2125 |
} else |
2126 |
i++; |
2127 |
|
1948 |
} |
2128 |
} |
1949 |
SWAP_PCTRIE_REMOVE(&object->un_pager.swp.swp_blks, sb->p); |
2129 |
SWAP_PCTRIE_REMOVE(&object->un_pager.swp.swp_blks, sb->p); |
1950 |
uma_zfree(swblk_zone, sb); |
2130 |
uma_zfree(swblk_zone, sb); |