|
@@ -146,6 +146,7 @@ static struct prop_descriptor vm_completions;
|
|
|
* We make sure that the background writeout level is below the adjusted
|
|
|
* clamping level.
|
|
|
*/
|
|
|
+
|
|
|
static unsigned long highmem_dirtyable_memory(unsigned long total)
|
|
|
{
|
|
|
#ifdef CONFIG_HIGHMEM
|
|
@@ -172,12 +173,12 @@ static unsigned long highmem_dirtyable_memory(unsigned long total)
|
|
|
}
|
|
|
|
|
|
/**
|
|
|
- * determine_dirtyable_memory - amount of memory that may be used
|
|
|
+ * global_dirtyable_memory - number of globally dirtyable pages
|
|
|
*
|
|
|
- * Returns the numebr of pages that can currently be freed and used
|
|
|
- * by the kernel for direct mappings.
|
|
|
+ * Returns the global number of pages potentially available for dirty
|
|
|
+ * page cache. This is the base value for the global dirty limits.
|
|
|
*/
|
|
|
-static unsigned long determine_dirtyable_memory(void)
|
|
|
+unsigned long global_dirtyable_memory(void)
|
|
|
{
|
|
|
unsigned long x;
|
|
|
|
|
@@ -190,6 +191,47 @@ static unsigned long determine_dirtyable_memory(void)
|
|
|
return x + 1; /* Ensure that we never return 0 */
|
|
|
}
|
|
|
|
|
|
+/*
|
|
|
+ * global_dirty_limits - background-writeback and dirty-throttling thresholds
|
|
|
+ *
|
|
|
+ * Calculate the dirty thresholds based on sysctl parameters
|
|
|
+ * - vm.dirty_background_ratio or vm.dirty_background_bytes
|
|
|
+ * - vm.dirty_ratio or vm.dirty_bytes
|
|
|
+ * The dirty limits will be lifted by 1/4 for PF_LESS_THROTTLE (ie. nfsd) and
|
|
|
+ * real-time tasks.
|
|
|
+ */
|
|
|
+void global_dirty_limits(unsigned long *pbackground, unsigned long *pdirty)
|
|
|
+{
|
|
|
+ unsigned long background;
|
|
|
+ unsigned long dirty;
|
|
|
+ unsigned long uninitialized_var(available_memory);
|
|
|
+ struct task_struct *tsk;
|
|
|
+
|
|
|
+ if (!vm_dirty_bytes || !dirty_background_bytes)
|
|
|
+ available_memory = global_dirtyable_memory();
|
|
|
+
|
|
|
+ if (vm_dirty_bytes)
|
|
|
+ dirty = DIV_ROUND_UP(vm_dirty_bytes, PAGE_SIZE);
|
|
|
+ else
|
|
|
+ dirty = (vm_dirty_ratio * available_memory) / 100;
|
|
|
+
|
|
|
+ if (dirty_background_bytes)
|
|
|
+ background = DIV_ROUND_UP(dirty_background_bytes, PAGE_SIZE);
|
|
|
+ else
|
|
|
+ background = (dirty_background_ratio * available_memory) / 100;
|
|
|
+
|
|
|
+ if (background >= dirty)
|
|
|
+ background = dirty / 2;
|
|
|
+ tsk = current;
|
|
|
+ if (tsk->flags & PF_LESS_THROTTLE || rt_task(tsk)) {
|
|
|
+ background += background / 4;
|
|
|
+ dirty += dirty / 4;
|
|
|
+ }
|
|
|
+ *pbackground = background;
|
|
|
+ *pdirty = dirty;
|
|
|
+ trace_global_dirty_state(background, dirty);
|
|
|
+}
|
|
|
+
|
|
|
/*
|
|
|
* couple the period to the dirty_ratio:
|
|
|
*
|
|
@@ -202,7 +244,7 @@ static int calc_period_shift(void)
|
|
|
if (vm_dirty_bytes)
|
|
|
dirty_total = vm_dirty_bytes / PAGE_SIZE;
|
|
|
else
|
|
|
- dirty_total = (vm_dirty_ratio * determine_dirtyable_memory()) /
|
|
|
+ dirty_total = (vm_dirty_ratio * global_dirtyable_memory()) /
|
|
|
100;
|
|
|
return 2 + ilog2(dirty_total - 1);
|
|
|
}
|
|
@@ -362,47 +404,6 @@ static unsigned long hard_dirty_limit(unsigned long thresh)
|
|
|
return max(thresh, global_dirty_limit);
|
|
|
}
|
|
|
|
|
|
-/*
|
|
|
- * global_dirty_limits - background-writeback and dirty-throttling thresholds
|
|
|
- *
|
|
|
- * Calculate the dirty thresholds based on sysctl parameters
|
|
|
- * - vm.dirty_background_ratio or vm.dirty_background_bytes
|
|
|
- * - vm.dirty_ratio or vm.dirty_bytes
|
|
|
- * The dirty limits will be lifted by 1/4 for PF_LESS_THROTTLE (ie. nfsd) and
|
|
|
- * real-time tasks.
|
|
|
- */
|
|
|
-void global_dirty_limits(unsigned long *pbackground, unsigned long *pdirty)
|
|
|
-{
|
|
|
- unsigned long background;
|
|
|
- unsigned long dirty;
|
|
|
- unsigned long uninitialized_var(available_memory);
|
|
|
- struct task_struct *tsk;
|
|
|
-
|
|
|
- if (!vm_dirty_bytes || !dirty_background_bytes)
|
|
|
- available_memory = determine_dirtyable_memory();
|
|
|
-
|
|
|
- if (vm_dirty_bytes)
|
|
|
- dirty = DIV_ROUND_UP(vm_dirty_bytes, PAGE_SIZE);
|
|
|
- else
|
|
|
- dirty = (vm_dirty_ratio * available_memory) / 100;
|
|
|
-
|
|
|
- if (dirty_background_bytes)
|
|
|
- background = DIV_ROUND_UP(dirty_background_bytes, PAGE_SIZE);
|
|
|
- else
|
|
|
- background = (dirty_background_ratio * available_memory) / 100;
|
|
|
-
|
|
|
- if (background >= dirty)
|
|
|
- background = dirty / 2;
|
|
|
- tsk = current;
|
|
|
- if (tsk->flags & PF_LESS_THROTTLE || rt_task(tsk)) {
|
|
|
- background += background / 4;
|
|
|
- dirty += dirty / 4;
|
|
|
- }
|
|
|
- *pbackground = background;
|
|
|
- *pdirty = dirty;
|
|
|
- trace_global_dirty_state(background, dirty);
|
|
|
-}
|
|
|
-
|
|
|
/**
|
|
|
* bdi_dirty_limit - @bdi's share of dirty throttling threshold
|
|
|
* @bdi: the backing_dev_info to query
|