2 * SYSCALL_DEFINE6(move_pages, pid_t, pid, unsigned long, nr_pages,
3 const void __user * __user *, pages,
4 const int __user *, nodes,
5 int __user *, status, int, flags)
8 #define MPOL_MF_MOVE (1<<1) /* Move pages owned by this process to conform to mapping */
9 #define MPOL_MF_MOVE_ALL (1<<2) /* Move every page to conform to mapping */
15 #include <sys/types.h>
21 #include "utils.h" // page_size
23 static unsigned int count
;
28 static unsigned char *pagetypes
;
30 /* After a succesful run, ->post calls this, which frees up
31 * the allocations done by ->sanitise */
32 static void free_all_pageallocs(unsigned long *page_alloc
)
36 if (pagetypes
== NULL
)
39 while (pagetypes
[i
] != NOT_SET
) {
40 /* we only care about freeing mallocs, ignore the mmaps. */
41 if (pagetypes
[i
] == WAS_MALLOC
) {
42 free((void *)page_alloc
[i
]);
44 pagetypes
[i
] = NOT_SET
;
51 static void sanitise_move_pages(int childno
)
55 unsigned long *page_alloc
;
58 if (pagetypes
== NULL
)
59 pagetypes
= zmalloc(page_size
); // The implied memset(0) == NOT_SET
61 /* number of pages to move */
62 count
= rand() % (page_size
/ sizeof(void *));
63 count
= max(1, count
);
64 shm
->a2
[childno
] = count
;
66 /* setup array of ptrs to pages to move */
67 page_alloc
= (unsigned long *) zmalloc(page_size
);
68 shm
->scratch
[childno
] = (unsigned long) page_alloc
;
70 for (i
= 0; i
< count
; i
++) {
73 page_alloc
[i
] = (unsigned long) memalign(page_size
, page_size
);
75 free_all_pageallocs(page_alloc
);
78 pagetypes
[i
] = WAS_MALLOC
;
82 page_alloc
[i
] = (unsigned long) map
->ptr
;
83 pagetypes
[i
] = WAS_MAP
;
86 shm
->a3
[childno
] = (unsigned long) page_alloc
;
88 /* nodes = array of ints specifying desired location for each page */
89 nodes
= malloc(count
* sizeof(int));
90 for (i
= 0; i
< count
; i
++)
91 nodes
[i
] = (int) rand() % 2;
92 shm
->a4
[childno
] = (unsigned long) nodes
;
94 /* status = array of ints returning status of each page.*/
95 shm
->a5
[childno
] = (unsigned long) zmalloc(count
* sizeof(int));
97 /* Needs CAP_SYS_NICE */
99 shm
->a6
[childno
] &= ~MPOL_MF_MOVE_ALL
;
102 static void post_move_pages(int childno
)
106 page
= (void *) shm
->scratch
[childno
];
110 free_all_pageallocs(page
);
112 shm
->scratch
[childno
] = 0;
115 struct syscallentry syscall_move_pages
= {
116 .name
= "move_pages",
120 .arg2name
= "nr_pages",
123 .arg5name
= "status",
125 .arg6type
= ARG_LIST
,
128 .values
= { MPOL_MF_MOVE
, MPOL_MF_MOVE_ALL
},
131 .sanitise
= sanitise_move_pages
,
132 .post
= post_move_pages
,