Commit afcf938ee0aac4ef95b1a23bac704c6fbeb26de6

Authored by Andi Kleen
Committed by Andi Kleen
1 parent facb6011f3

HWPOISON: Add a madvise() injector for soft page offlining

Process based injection is much easier to handle for test programs,
who can first bring a page into a specific state and then test.
So add a new MADV_SOFT_OFFLINE to soft offline a page, similar
to the existing hard offline injector.

Signed-off-by: Andi Kleen <ak@linux.intel.com>

Showing 2 changed files with 13 additions and 3 deletions Side-by-side Diff

include/asm-generic/mman-common.h
... ... @@ -40,6 +40,7 @@
40 40 #define MADV_DONTFORK 10 /* don't inherit across fork */
41 41 #define MADV_DOFORK 11 /* do inherit across fork */
42 42 #define MADV_HWPOISON 100 /* poison a page for testing */
  43 +#define MADV_SOFT_OFFLINE 101 /* soft offline page for testing */
43 44  
44 45 #define MADV_MERGEABLE 12 /* KSM may merge identical pages */
45 46 #define MADV_UNMERGEABLE 13 /* KSM may not merge identical pages */
... ... @@ -9,6 +9,7 @@
9 9 #include <linux/pagemap.h>
10 10 #include <linux/syscalls.h>
11 11 #include <linux/mempolicy.h>
  12 +#include <linux/page-isolation.h>
12 13 #include <linux/hugetlb.h>
13 14 #include <linux/sched.h>
14 15 #include <linux/ksm.h>
... ... @@ -222,7 +223,7 @@
222 223 /*
223 224 * Error injection support for memory error handling.
224 225 */
225   -static int madvise_hwpoison(unsigned long start, unsigned long end)
  226 +static int madvise_hwpoison(int bhv, unsigned long start, unsigned long end)
226 227 {
227 228 int ret = 0;
228 229  
... ... @@ -233,6 +234,14 @@
233 234 int ret = get_user_pages_fast(start, 1, 0, &p);
234 235 if (ret != 1)
235 236 return ret;
  237 + if (bhv == MADV_SOFT_OFFLINE) {
  238 + printk(KERN_INFO "Soft offlining page %lx at %lx\n",
  239 + page_to_pfn(p), start);
  240 + ret = soft_offline_page(p, MF_COUNT_INCREASED);
  241 + if (ret)
  242 + break;
  243 + continue;
  244 + }
236 245 printk(KERN_INFO "Injecting memory failure for page %lx at %lx\n",
237 246 page_to_pfn(p), start);
238 247 /* Ignore return value for now */
... ... @@ -333,8 +342,8 @@
333 342 size_t len;
334 343  
335 344 #ifdef CONFIG_MEMORY_FAILURE
336   - if (behavior == MADV_HWPOISON)
337   - return madvise_hwpoison(start, start+len_in);
  345 + if (behavior == MADV_HWPOISON || behavior == MADV_SOFT_OFFLINE)
  346 + return madvise_hwpoison(behavior, start, start+len_in);
338 347 #endif
339 348 if (!madvise_behavior_valid(behavior))
340 349 return error;