diff options
-rw-r--r-- | kernel/power/power.h | 14 | ||||
-rw-r--r-- | kernel/power/user.c | 31 |
2 files changed, 44 insertions, 1 deletions
diff --git a/kernel/power/power.h b/kernel/power/power.h index adaf7d4fbdaf..7dbfd9f67e1c 100644 --- a/kernel/power/power.h +++ b/kernel/power/power.h | |||
@@ -106,6 +106,16 @@ extern int snapshot_write_next(struct snapshot_handle *handle, size_t count); | |||
106 | extern int snapshot_image_loaded(struct snapshot_handle *handle); | 106 | extern int snapshot_image_loaded(struct snapshot_handle *handle); |
107 | extern void snapshot_free_unused_memory(struct snapshot_handle *handle); | 107 | extern void snapshot_free_unused_memory(struct snapshot_handle *handle); |
108 | 108 | ||
109 | /* | ||
110 | * This structure is used to pass the values needed for the identification | ||
111 | * of the resume swap area from a user space to the kernel via the | ||
112 | * SNAPSHOT_SET_SWAP_AREA ioctl | ||
113 | */ | ||
114 | struct resume_swap_area { | ||
115 | loff_t offset; | ||
116 | u_int32_t dev; | ||
117 | } __attribute__((packed)); | ||
118 | |||
109 | #define SNAPSHOT_IOC_MAGIC '3' | 119 | #define SNAPSHOT_IOC_MAGIC '3' |
110 | #define SNAPSHOT_FREEZE _IO(SNAPSHOT_IOC_MAGIC, 1) | 120 | #define SNAPSHOT_FREEZE _IO(SNAPSHOT_IOC_MAGIC, 1) |
111 | #define SNAPSHOT_UNFREEZE _IO(SNAPSHOT_IOC_MAGIC, 2) | 121 | #define SNAPSHOT_UNFREEZE _IO(SNAPSHOT_IOC_MAGIC, 2) |
@@ -119,7 +129,9 @@ extern void snapshot_free_unused_memory(struct snapshot_handle *handle); | |||
119 | #define SNAPSHOT_SET_SWAP_FILE _IOW(SNAPSHOT_IOC_MAGIC, 10, unsigned int) | 129 | #define SNAPSHOT_SET_SWAP_FILE _IOW(SNAPSHOT_IOC_MAGIC, 10, unsigned int) |
120 | #define SNAPSHOT_S2RAM _IO(SNAPSHOT_IOC_MAGIC, 11) | 130 | #define SNAPSHOT_S2RAM _IO(SNAPSHOT_IOC_MAGIC, 11) |
121 | #define SNAPSHOT_PMOPS _IOW(SNAPSHOT_IOC_MAGIC, 12, unsigned int) | 131 | #define SNAPSHOT_PMOPS _IOW(SNAPSHOT_IOC_MAGIC, 12, unsigned int) |
122 | #define SNAPSHOT_IOC_MAXNR 12 | 132 | #define SNAPSHOT_SET_SWAP_AREA _IOW(SNAPSHOT_IOC_MAGIC, 13, \ |
133 | struct resume_swap_area) | ||
134 | #define SNAPSHOT_IOC_MAXNR 13 | ||
123 | 135 | ||
124 | #define PMOPS_PREPARE 1 | 136 | #define PMOPS_PREPARE 1 |
125 | #define PMOPS_ENTER 2 | 137 | #define PMOPS_ENTER 2 |
diff --git a/kernel/power/user.c b/kernel/power/user.c index f0b7ef8bdd74..05c58a2c0dd4 100644 --- a/kernel/power/user.c +++ b/kernel/power/user.c | |||
@@ -343,6 +343,37 @@ OutS3: | |||
343 | } | 343 | } |
344 | break; | 344 | break; |
345 | 345 | ||
346 | case SNAPSHOT_SET_SWAP_AREA: | ||
347 | if (data->bitmap) { | ||
348 | error = -EPERM; | ||
349 | } else { | ||
350 | struct resume_swap_area swap_area; | ||
351 | dev_t swdev; | ||
352 | |||
353 | error = copy_from_user(&swap_area, (void __user *)arg, | ||
354 | sizeof(struct resume_swap_area)); | ||
355 | if (error) { | ||
356 | error = -EFAULT; | ||
357 | break; | ||
358 | } | ||
359 | |||
360 | /* | ||
361 | * User space encodes device types as two-byte values, | ||
362 | * so we need to recode them | ||
363 | */ | ||
364 | swdev = old_decode_dev(swap_area.dev); | ||
365 | if (swdev) { | ||
366 | offset = swap_area.offset; | ||
367 | data->swap = swap_type_of(swdev, offset); | ||
368 | if (data->swap < 0) | ||
369 | error = -ENODEV; | ||
370 | } else { | ||
371 | data->swap = -1; | ||
372 | error = -EINVAL; | ||
373 | } | ||
374 | } | ||
375 | break; | ||
376 | |||
346 | default: | 377 | default: |
347 | error = -ENOTTY; | 378 | error = -ENOTTY; |
348 | 379 | ||