+ swsusp-use-partition-device-and-offset-to-identify-swap-areas.patch added to -mm tree

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



The patch titled

     swsusp: use partition device and offset to identify swap areas

has been added to the -mm tree.  Its filename is

     swsusp-use-partition-device-and-offset-to-identify-swap-areas.patch

See http://www.zip.com.au/~akpm/linux/patches/stuff/added-to-mm.txt to find
out what to do about this

------------------------------------------------------
Subject: swsusp: use partition device and offset to identify swap areas
From: "Rafael J. Wysocki" <rjw@xxxxxxx>

The Linux kernel handles swap files almost in the same way as it handles swap
partitions and there are only two differences between these two types of swap
areas:

(1) swap files need not be contiguous,

(2) the header of a swap file is not in the first block of the partition
    that holds it.  From the swsusp's point of view (1) is not a problem,
    because it is already taken care of by the swap-handling code, but (2) has
    to be taken into consideration.

In principle the location of a swap file's header may be determined with the
help of appropriate filesystem driver.  Unfortunately, however, it requires
the filesystem holding the swap file to be mounted, and if this filesystem is
journaled, it cannot be mounted during a resume from disk.  For this reason we
need some other means by which swap areas can be identified.

For example, to identify a swap area we can use the partition that holds the
area and the offset from the beginning of this partition at which the swap
header is located.

The following patch allows swsusp to identify swap areas this way.  It changes
swap_type_of() so that it takes an additional argument representing an offset
of the swap header within the partition represented by its first argument.

Signed-off-by: Rafael J. Wysocki <rjw@xxxxxxx>
Acked-by: Pavel Machek <pavel@xxxxxx>
Signed-off-by: Andrew Morton <akpm@xxxxxxxx>
---

 include/linux/swap.h |    2 +-
 kernel/power/swap.c  |    2 +-
 kernel/power/user.c  |    5 +++--
 mm/swapfile.c        |   38 ++++++++++++++++++++++++++------------
 4 files changed, 31 insertions(+), 16 deletions(-)

diff -puN include/linux/swap.h~swsusp-use-partition-device-and-offset-to-identify-swap-areas include/linux/swap.h
--- a/include/linux/swap.h~swsusp-use-partition-device-and-offset-to-identify-swap-areas
+++ a/include/linux/swap.h
@@ -247,7 +247,7 @@ extern int swap_duplicate(swp_entry_t);
 extern int valid_swaphandles(swp_entry_t, unsigned long *);
 extern void swap_free(swp_entry_t);
 extern void free_swap_and_cache(swp_entry_t);
-extern int swap_type_of(dev_t);
+extern int swap_type_of(dev_t, sector_t);
 extern unsigned int count_swap_pages(int, int);
 extern sector_t map_swap_page(struct swap_info_struct *, pgoff_t);
 extern struct swap_info_struct *get_swap_info_struct(unsigned);
diff -puN kernel/power/swap.c~swsusp-use-partition-device-and-offset-to-identify-swap-areas kernel/power/swap.c
--- a/kernel/power/swap.c~swsusp-use-partition-device-and-offset-to-identify-swap-areas
+++ a/kernel/power/swap.c
@@ -74,7 +74,7 @@ static int mark_swapfiles(swp_entry_t st
 
 static int swsusp_swap_check(void) /* This is called before saving image */
 {
-	int res = swap_type_of(swsusp_resume_device);
+	int res = swap_type_of(swsusp_resume_device, 0);
 
 	if (res >= 0) {
 		root_swap = res;
diff -puN kernel/power/user.c~swsusp-use-partition-device-and-offset-to-identify-swap-areas kernel/power/user.c
--- a/kernel/power/user.c~swsusp-use-partition-device-and-offset-to-identify-swap-areas
+++ a/kernel/power/user.c
@@ -55,7 +55,8 @@ static int snapshot_open(struct inode *i
 	filp->private_data = data;
 	memset(&data->handle, 0, sizeof(struct snapshot_handle));
 	if ((filp->f_flags & O_ACCMODE) == O_RDONLY) {
-		data->swap = swsusp_resume_device ? swap_type_of(swsusp_resume_device) : -1;
+		data->swap = swsusp_resume_device ?
+				swap_type_of(swsusp_resume_device, 0) : -1;
 		data->mode = O_RDONLY;
 	} else {
 		data->swap = -1;
@@ -265,7 +266,7 @@ static int snapshot_ioctl(struct inode *
 			 * so we need to recode them
 			 */
 			if (old_decode_dev(arg)) {
-				data->swap = swap_type_of(old_decode_dev(arg));
+				data->swap = swap_type_of(old_decode_dev(arg), 0);
 				if (data->swap < 0)
 					error = -ENODEV;
 			} else {
diff -puN mm/swapfile.c~swsusp-use-partition-device-and-offset-to-identify-swap-areas mm/swapfile.c
--- a/mm/swapfile.c~swsusp-use-partition-device-and-offset-to-identify-swap-areas
+++ a/mm/swapfile.c
@@ -427,34 +427,48 @@ void free_swap_and_cache(swp_entry_t ent
 
 #ifdef CONFIG_SOFTWARE_SUSPEND
 /*
- * Find the swap type that corresponds to given device (if any)
+ * Find the swap type that corresponds to given device (if any).
  *
- * This is needed for software suspend and is done in such a way that inode
- * aliasing is allowed.
+ * @offset - number of the PAGE_SIZE-sized block of the device, starting
+ * from 0, in which the swap header is expected to be located.
+ *
+ * This is needed for the suspend to disk (aka swsusp).
  */
-int swap_type_of(dev_t device)
+int swap_type_of(dev_t device, sector_t offset)
 {
+	struct block_device *bdev = NULL;
 	int i;
 
+	if (device)
+		bdev = bdget(device);
+
 	spin_lock(&swap_lock);
 	for (i = 0; i < nr_swapfiles; i++) {
-		struct inode *inode;
+		struct swap_info_struct *sis = swap_info + i;
 
-		if (!(swap_info[i].flags & SWP_WRITEOK))
+		if (!(sis->flags & SWP_WRITEOK))
 			continue;
 
-		if (!device) {
+		if (!bdev) {
 			spin_unlock(&swap_lock);
 			return i;
 		}
-		inode = swap_info[i].swap_file->f_dentry->d_inode;
-		if (S_ISBLK(inode->i_mode) &&
-		    device == MKDEV(imajor(inode), iminor(inode))) {
-			spin_unlock(&swap_lock);
-			return i;
+		if (bdev == sis->bdev) {
+			struct swap_extent *se;
+
+			se = list_entry(sis->extent_list.next,
+					struct swap_extent, list);
+			if (se->start_block == offset) {
+				spin_unlock(&swap_lock);
+				bdput(bdev);
+				return i;
+			}
 		}
 	}
 	spin_unlock(&swap_lock);
+	if (bdev)
+		bdput(bdev);
+
 	return -ENODEV;
 }
 
_

Patches currently in -mm which might be from rjw@xxxxxxx are

origin.patch
usb-allow-both-root-hub-interrupts-and-polling.patch
ohci-remove-existing-autosuspend-code.patch
ohci-add-auto-stop-support.patch
ohci-add-auto-stop-support-hack-hack.patch
uswsusp-add-pmops-prepareenterfinish-support-aka-platform-mode.patch
swsusp-use-suspend_console.patch
swsusp-use-partition-device-and-offset-to-identify-swap-areas.patch
swsusp-rearrange-swap-handling-code.patch
swsusp-use-block-device-offsets-to-identify-swap-locations-rev-2.patch
swsusp-add-resume_offset-command-line-parameter-rev-2.patch
swsusp-add-resume_offset-command-line-parameter-rev-2-fix.patch
swsusp-document-support-for-swap-files-rev-2.patch
reiserfs-make-sure-all-dentries-refs-are-released-before-calling-kill_block_super-try-2.patch
ide-reprogram-disk-pio-timings-on-resume.patch

-
To unsubscribe from this list: send the line "unsubscribe mm-commits" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Kernel Newbies FAQ]     [Kernel Archive]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [Bugtraq]     [Photo]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]

  Powered by Linux