Staging: ramzswap: Remove backing swap support
authorNitin Gupta <ngupta@vflare.org>
Thu, 13 May 2010 08:54:21 +0000 (14:24 +0530)
committerGreg Kroah-Hartman <gregkh@suse.de>
Fri, 14 May 2010 20:25:28 +0000 (13:25 -0700)
Currently, each ramzswap device can be assigned
a separate 'backing swap' file/partition. The ramzswap
driver forwards swap I/O requests to this backing swap
whenever an incompressible page is found.

This feature adds nearly 700 lines of code and it
also duplicates much of the swapon() functionality
(for example, finding swap extents and so on). Removing
this code makes the driver much simpler and should
help its transition from staging to stable drivers
area (drivers/block/).

Similar functionality may be implemented if we can
implement migrating pages across swap devices but the
details have not yet been worked out.

Support for _partitions_ as backing swap could be
retained as it requires a few lines of code only.
This part can be re-introduced later if above swap
migration method turns out to be infeasible.

More cleanups and code comments will be added soon.

Signed-off-by: Nitin Gupta <ngupta@vflare.org>
Acked-by: Pekka Enberg <penberg@cs.helsinki.fi>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
drivers/staging/ramzswap/ramzswap_drv.c
drivers/staging/ramzswap/ramzswap_drv.h
drivers/staging/ramzswap/ramzswap_ioctl.h

index ee5eb12..167f8d1 100644 (file)
 static int ramzswap_major;
 static struct ramzswap *devices;
 
-/*
- * Pages that compress to larger than this size are
- * forwarded to backing swap, if present or stored
- * uncompressed in memory otherwise.
- */
-static unsigned int max_zpage_size;
-
 /* Module params (documentation at end) */
 static unsigned int num_devices;
 
@@ -79,52 +72,6 @@ static int page_zero_filled(void *ptr)
        return 1;
 }
 
-/*
- * memlimit cannot be greater than backing disk size.
- */
-static void ramzswap_set_memlimit(struct ramzswap *rzs, size_t totalram_bytes)
-{
-       int memlimit_valid = 1;
-
-       if (!rzs->memlimit) {
-               pr_info("Memory limit not set.\n");
-               memlimit_valid = 0;
-       }
-
-       if (rzs->memlimit > rzs->disksize) {
-               pr_info("Memory limit cannot be greater than "
-                       "disksize: limit=%zu, disksize=%zu\n",
-                       rzs->memlimit, rzs->disksize);
-               memlimit_valid = 0;
-       }
-
-       if (!memlimit_valid) {
-               size_t mempart, disksize;
-               pr_info("Using default: smaller of (%u%% of RAM) and "
-                       "(backing disk size).\n",
-                       default_memlimit_perc_ram);
-               mempart = default_memlimit_perc_ram * (totalram_bytes / 100);
-               disksize = rzs->disksize;
-               rzs->memlimit = mempart > disksize ? disksize : mempart;
-       }
-
-       if (rzs->memlimit > totalram_bytes / 2) {
-               pr_info(
-               "Its not advisable setting limit more than half of "
-               "size of memory since we expect a 2:1 compression ratio. "
-               "Limit represents amount of *compressed* data we can keep "
-               "in memory!\n"
-               "\tMemory Size: %zu kB\n"
-               "\tLimit you selected: %zu kB\n"
-               "Continuing anyway ...\n",
-               totalram_bytes >> 10, rzs->memlimit >> 10
-               );
-       }
-
-       rzs->memlimit &= PAGE_MASK;
-       BUG_ON(!rzs->memlimit);
-}
-
 static void ramzswap_set_disksize(struct ramzswap *rzs, size_t totalram_bytes)
 {
        if (!rzs->disksize) {
@@ -156,80 +103,22 @@ static void ramzswap_set_disksize(struct ramzswap *rzs, size_t totalram_bytes)
 
 /*
  * Swap header (1st page of swap device) contains information
- * to indentify it as a swap partition. Prepare such a header
- * for ramzswap device (ramzswap0) so that swapon can identify
- * it as swap partition. In case backing swap device is provided,
- * copy its swap header.
+ * about a swap file/partition. Prepare such a header for the
+ * given ramzswap device so that swapon can identify it as a
+ * swap partition.
  */
-static int setup_swap_header(struct ramzswap *rzs, union swap_header *s)
+static void setup_swap_header(struct ramzswap *rzs, union swap_header *s)
 {
-       int ret = 0;
-       struct page *page;
-       struct address_space *mapping;
-       union swap_header *backing_swap_header;
-
-       /*
-        * There is no backing swap device. Create a swap header
-        * that is acceptable by swapon.
-        */
-       if (!rzs->backing_swap) {
-               s->info.version = 1;
-               s->info.last_page = (rzs->disksize >> PAGE_SHIFT) - 1;
-               s->info.nr_badpages = 0;
-               memcpy(s->magic.magic, "SWAPSPACE2", 10);
-               return 0;
-       }
-
-       /*
-        * We have a backing swap device. Copy its swap header
-        * to ramzswap device header. If this header contains
-        * invalid information (backing device not a swap
-        * partition, etc.), swapon will fail for ramzswap
-        * which is correct behavior - we don't want to swap
-        * over filesystem partition!
-        */
-
-       /* Read the backing swap header (code from sys_swapon) */
-       mapping = rzs->swap_file->f_mapping;
-       if (!mapping->a_ops->readpage) {
-               ret = -EINVAL;
-               goto out;
-       }
-
-       page = read_mapping_page(mapping, 0, rzs->swap_file);
-       if (IS_ERR(page)) {
-               ret = PTR_ERR(page);
-               goto out;
-       }
-
-       backing_swap_header = kmap(page);
-       memcpy(s, backing_swap_header, sizeof(*s));
-       if (s->info.nr_badpages) {
-               pr_info("Cannot use backing swap with bad pages (%u)\n",
-                       s->info.nr_badpages);
-               ret = -EINVAL;
-       }
-       /*
-        * ramzswap disksize equals number of usable pages in backing
-        * swap. Set last_page in swap header to match this disksize
-        * ('last_page' means 0-based index of last usable swap page).
-        */
+       s->info.version = 1;
        s->info.last_page = (rzs->disksize >> PAGE_SHIFT) - 1;
-       kunmap(page);
-
-out:
-       return ret;
+       s->info.nr_badpages = 0;
+       memcpy(s->magic.magic, "SWAPSPACE2", 10);
 }
 
 static void ramzswap_ioctl_get_stats(struct ramzswap *rzs,
                        struct ramzswap_ioctl_stats *s)
 {
-       strncpy(s->backing_swap_name, rzs->backing_swap_name,
-               MAX_SWAP_NAME_LEN - 1);
-       s->backing_swap_name[MAX_SWAP_NAME_LEN - 1] = '\0';
-
        s->disksize = rzs->disksize;
-       s->memlimit = rzs->memlimit;
 
 #if defined(CONFIG_RAMZSWAP_STATS)
        {
@@ -265,333 +154,10 @@ static void ramzswap_ioctl_get_stats(struct ramzswap *rzs,
        s->orig_data_size = rs->pages_stored << PAGE_SHIFT;
        s->compr_data_size = rs->compr_size;
        s->mem_used_total = mem_used;
-
-       s->bdev_num_reads = rzs_stat64_read(rzs, &rs->bdev_num_reads);
-       s->bdev_num_writes = rzs_stat64_read(rzs, &rs->bdev_num_writes);
        }
 #endif /* CONFIG_RAMZSWAP_STATS */
 }
 
-static int add_backing_swap_extent(struct ramzswap *rzs,
-                               pgoff_t phy_pagenum,
-                               pgoff_t num_pages)
-{
-       unsigned int idx;
-       struct list_head *head;
-       struct page *curr_page, *new_page;
-       unsigned int extents_per_page = PAGE_SIZE /
-                               sizeof(struct ramzswap_backing_extent);
-
-       idx = rzs->num_extents % extents_per_page;
-       if (!idx) {
-               new_page = alloc_page(__GFP_ZERO);
-               if (!new_page)
-                       return -ENOMEM;
-
-               if (rzs->num_extents) {
-                       curr_page = virt_to_page(rzs->curr_extent);
-                       head = &curr_page->lru;
-               } else {
-                       head = &rzs->backing_swap_extent_list;
-               }
-
-               list_add(&new_page->lru, head);
-               rzs->curr_extent = page_address(new_page);
-       }
-
-       rzs->curr_extent->phy_pagenum = phy_pagenum;
-       rzs->curr_extent->num_pages = num_pages;
-
-       pr_debug("add_extent: idx=%u, phy_pgnum=%lu, num_pgs=%lu, "
-               "pg_last=%lu, curr_ext=%p\n", idx, phy_pagenum, num_pages,
-               phy_pagenum + num_pages - 1, rzs->curr_extent);
-
-       if (idx != extents_per_page - 1)
-               rzs->curr_extent++;
-
-       return 0;
-}
-
-static int setup_backing_swap_extents(struct ramzswap *rzs,
-                               struct inode *inode, unsigned long *num_pages)
-{
-       int ret = 0;
-       unsigned blkbits;
-       unsigned blocks_per_page;
-       pgoff_t contig_pages = 0, total_pages = 0;
-       pgoff_t pagenum = 0, prev_pagenum = 0;
-       sector_t probe_block = 0;
-       sector_t last_block;
-
-       blkbits = inode->i_blkbits;
-       blocks_per_page = PAGE_SIZE >> blkbits;
-
-       last_block = i_size_read(inode) >> blkbits;
-       while (probe_block + blocks_per_page <= last_block) {
-               unsigned block_in_page;
-               sector_t first_block;
-
-               first_block = bmap(inode, probe_block);
-               if (first_block == 0)
-                       goto bad_bmap;
-
-               /* It must be PAGE_SIZE aligned on-disk */
-               if (first_block & (blocks_per_page - 1)) {
-                       probe_block++;
-                       goto probe_next;
-               }
-
-               /* All blocks within this page must be contiguous on disk */
-               for (block_in_page = 1; block_in_page < blocks_per_page;
-                                       block_in_page++) {
-                       sector_t block;
-
-                       block = bmap(inode, probe_block + block_in_page);
-                       if (block == 0)
-                               goto bad_bmap;
-                       if (block != first_block + block_in_page) {
-                               /* Discontiguity */
-                               probe_block++;
-                               goto probe_next;
-                       }
-               }
-
-               /*
-                * We found a PAGE_SIZE length, PAGE_SIZE aligned
-                * run of blocks.
-                */
-               pagenum = first_block >> (PAGE_SHIFT - blkbits);
-
-               if (total_pages && (pagenum != prev_pagenum + 1)) {
-                       ret = add_backing_swap_extent(rzs, prev_pagenum -
-                                       (contig_pages - 1), contig_pages);
-                       if (ret < 0)
-                               goto out;
-                       rzs->num_extents++;
-                       contig_pages = 0;
-               }
-               total_pages++;
-               contig_pages++;
-               prev_pagenum = pagenum;
-               probe_block += blocks_per_page;
-
-probe_next:
-               continue;
-       }
-
-       if (contig_pages) {
-               pr_debug("adding last extent: pagenum=%lu, "
-                       "contig_pages=%lu\n", pagenum, contig_pages);
-               ret = add_backing_swap_extent(rzs,
-                       prev_pagenum - (contig_pages - 1), contig_pages);
-               if (ret < 0)
-                       goto out;
-               rzs->num_extents++;
-       }
-       if (!rzs->num_extents) {
-               pr_err("No swap extents found!\n");
-               ret = -EINVAL;
-       }
-
-       if (!ret) {
-               *num_pages = total_pages;
-               pr_info("Found %lu extents containing %luk\n",
-                       rzs->num_extents, *num_pages << (PAGE_SHIFT - 10));
-       }
-       goto out;
-
-bad_bmap:
-       pr_err("Backing swapfile has holes\n");
-       ret = -EINVAL;
-out:
-       while (ret && !list_empty(&rzs->backing_swap_extent_list)) {
-               struct page *page;
-               struct list_head *entry = rzs->backing_swap_extent_list.next;
-               page = list_entry(entry, struct page, lru);
-               list_del(entry);
-               __free_page(page);
-       }
-       return ret;
-}
-
-static void map_backing_swap_extents(struct ramzswap *rzs)
-{
-       struct ramzswap_backing_extent *se;
-       struct page *table_page, *se_page;
-       unsigned long num_pages, num_table_pages, entry;
-       unsigned long se_idx, span;
-       unsigned entries_per_page = PAGE_SIZE / sizeof(*rzs->table);
-       unsigned extents_per_page = PAGE_SIZE / sizeof(*se);
-
-       /* True for block device */
-       if (!rzs->num_extents)
-               return;
-
-       se_page = list_entry(rzs->backing_swap_extent_list.next,
-                                       struct page, lru);
-       se = page_address(se_page);
-       span = se->num_pages;
-       num_pages = rzs->disksize >> PAGE_SHIFT;
-       num_table_pages = DIV_ROUND_UP(num_pages * sizeof(*rzs->table),
-                                                       PAGE_SIZE);
-
-       entry = 0;
-       se_idx = 0;
-       while (num_table_pages--) {
-               table_page = vmalloc_to_page(&rzs->table[entry]);
-               while (span <= entry) {
-                       se_idx++;
-                       if (se_idx == rzs->num_extents)
-                               BUG();
-
-                       if (!(se_idx % extents_per_page)) {
-                               se_page = list_entry(se_page->lru.next,
-                                               struct page, lru);
-                               se = page_address(se_page);
-                       } else
-                               se++;
-
-                       span += se->num_pages;
-               }
-               table_page->mapping = (struct address_space *)se;
-               table_page->private = se->num_pages - (span - entry);
-               pr_debug("map_table: entry=%lu, span=%lu, map=%p, priv=%lu\n",
-                       entry, span, table_page->mapping, table_page->private);
-               entry += entries_per_page;
-       }
-}
-
-/*
- * Check if value of backing_swap module param is sane.
- * Claim this device and set ramzswap size equal to
- * size of this block device.
- */
-static int setup_backing_swap(struct ramzswap *rzs)
-{
-       int ret = 0;
-       size_t disksize;
-       unsigned long num_pages = 0;
-       struct inode *inode;
-       struct file *swap_file;
-       struct address_space *mapping;
-       struct block_device *bdev = NULL;
-
-       if (!rzs->backing_swap_name[0]) {
-               pr_debug("backing_swap param not given\n");
-               goto out;
-       }
-
-       pr_info("Using backing swap device: %s\n", rzs->backing_swap_name);
-
-       swap_file = filp_open(rzs->backing_swap_name,
-                               O_RDWR | O_LARGEFILE, 0);
-       if (IS_ERR(swap_file)) {
-               pr_err("Error opening backing device: %s\n",
-                       rzs->backing_swap_name);
-               ret = -EINVAL;
-               goto out;
-       }
-
-       mapping = swap_file->f_mapping;
-       inode = mapping->host;
-
-       if (S_ISBLK(inode->i_mode)) {
-               bdev = I_BDEV(inode);
-               ret = bd_claim(bdev, setup_backing_swap);
-               if (ret < 0) {
-                       bdev = NULL;
-                       goto bad_param;
-               }
-               disksize = i_size_read(inode);
-               /*
-                * Can happen if user gives an extended partition as
-                * backing swap or simply a bad disk.
-                */
-               if (!disksize) {
-                       pr_err("Error reading backing swap size.\n");
-                       goto bad_param;
-               }
-       } else if (S_ISREG(inode->i_mode)) {
-               bdev = inode->i_sb->s_bdev;
-               if (IS_SWAPFILE(inode)) {
-                       ret = -EBUSY;
-                       goto bad_param;
-               }
-               ret = setup_backing_swap_extents(rzs, inode, &num_pages);
-               if (ret < 0)
-                       goto bad_param;
-               disksize = num_pages << PAGE_SHIFT;
-       } else {
-               goto bad_param;
-       }
-
-       rzs->swap_file = swap_file;
-       rzs->backing_swap = bdev;
-       rzs->disksize = disksize;
-
-       return 0;
-
-bad_param:
-       if (bdev)
-               bd_release(bdev);
-       filp_close(swap_file, NULL);
-
-out:
-       rzs->backing_swap = NULL;
-       return ret;
-}
-
-/*
- * Map logical page number 'pagenum' to physical page number
- * on backing swap device. For block device, this is a nop.
- */
-static u32 map_backing_swap_page(struct ramzswap *rzs, u32 pagenum)
-{
-       u32 skip_pages, entries_per_page;
-       size_t delta, se_offset, skipped;
-       struct page *table_page, *se_page;
-       struct ramzswap_backing_extent *se;
-
-       if (!rzs->num_extents)
-               return pagenum;
-
-       entries_per_page = PAGE_SIZE / sizeof(*rzs->table);
-
-       table_page = vmalloc_to_page(&rzs->table[pagenum]);
-       se = (struct ramzswap_backing_extent *)table_page->mapping;
-       se_page = virt_to_page(se);
-
-       skip_pages = pagenum - (pagenum / entries_per_page * entries_per_page);
-       se_offset = table_page->private + skip_pages;
-
-       if (se_offset < se->num_pages)
-               return se->phy_pagenum + se_offset;
-
-       skipped = se->num_pages - table_page->private;
-       do {
-               struct ramzswap_backing_extent *se_base;
-               u32 se_entries_per_page = PAGE_SIZE / sizeof(*se);
-
-               /* Get next swap extent */
-               se_base = (struct ramzswap_backing_extent *)
-                                               page_address(se_page);
-               if (se - se_base == se_entries_per_page - 1) {
-                       se_page = list_entry(se_page->lru.next,
-                                               struct page, lru);
-                       se = page_address(se_page);
-               } else {
-                       se++;
-               }
-
-               skipped += se->num_pages;
-       } while (skipped < skip_pages);
-
-       delta = skipped - skip_pages;
-       se_offset = se->num_pages - delta;
-
-       return se->phy_pagenum + se_offset;
-}
-
 static void ramzswap_free_page(struct ramzswap *rzs, size_t index)
 {
        u32 clen;
@@ -678,38 +244,12 @@ static int handle_uncompressed_page(struct ramzswap *rzs, struct bio *bio)
 
 /*
  * Called when request page is not present in ramzswap.
- * Its either in backing swap device (if present) or
- * this is an attempt to read before any previous write
+ * This is an attempt to read before any previous write
  * to this location - this happens due to readahead when
  * swap device is read from user-space (e.g. during swapon)
  */
 static int handle_ramzswap_fault(struct ramzswap *rzs, struct bio *bio)
 {
-       /*
-        * Always forward such requests to backing swap
-        * device (if present)
-        */
-       if (rzs->backing_swap) {
-               u32 pagenum;
-               rzs_stat64_dec(rzs, &rzs->stats.num_reads);
-               rzs_stat64_inc(rzs, &rzs->stats.bdev_num_reads);
-               bio->bi_bdev = rzs->backing_swap;
-
-               /*
-                * In case backing swap is a file, find the right offset within
-                * the file corresponding to logical position 'index'. For block
-                * device, this is a nop.
-                */
-               pagenum = bio->bi_sector >> SECTORS_PER_PAGE_SHIFT;
-               bio->bi_sector = map_backing_swap_page(rzs, pagenum)
-                                       << SECTORS_PER_PAGE_SHIFT;
-               return 1;
-       }
-
-       /*
-        * Its unlikely event in case backing dev is
-        * not present
-        */
        pr_debug("Read before write on swap device: "
                "sector=%lu, size=%u, offset=%u\n",
                (ulong)(bio->bi_sector), bio->bi_size,
@@ -781,7 +321,7 @@ out:
 
 static int ramzswap_write(struct ramzswap *rzs, struct bio *bio)
 {
-       int ret, fwd_write_request = 0;
+       int ret;
        u32 offset, index;
        size_t clen;
        struct zobj_header *zheader;
@@ -817,14 +357,6 @@ static int ramzswap_write(struct ramzswap *rzs, struct bio *bio)
                return 0;
        }
 
-       if (rzs->backing_swap &&
-               (rzs->stats.compr_size > rzs->memlimit - PAGE_SIZE)) {
-               kunmap_atomic(user_mem, KM_USER0);
-               mutex_unlock(&rzs->lock);
-               fwd_write_request = 1;
-               goto out;
-       }
-
        ret = lzo1x_1_compress(user_mem, PAGE_SIZE, src, &clen,
                                rzs->compress_workmem);
 
@@ -838,18 +370,11 @@ static int ramzswap_write(struct ramzswap *rzs, struct bio *bio)
        }
 
        /*
-        * Page is incompressible. Forward it to backing swap
-        * if present. Otherwise, store it as-is (uncompressed)
+        * Page is incompressible. Store it as-is (uncompressed)
         * since we do not want to return too many swap write
         * errors which has side effect of hanging the system.
         */
        if (unlikely(clen > max_zpage_size)) {
-               if (rzs->backing_swap) {
-                       mutex_unlock(&rzs->lock);
-                       fwd_write_request = 1;
-                       goto out;
-               }
-
                clen = PAGE_SIZE;
                page_store = alloc_page(GFP_NOIO | __GFP_HIGHMEM);
                if (unlikely(!page_store)) {
@@ -875,8 +400,6 @@ static int ramzswap_write(struct ramzswap *rzs, struct bio *bio)
                pr_info("Error allocating memory for compressed "
                        "page: %u, size=%zu\n", index, clen);
                rzs_stat64_inc(rzs, &rzs->stats.failed_writes);
-               if (rzs->backing_swap)
-                       fwd_write_request = 1;
                goto out;
        }
 
@@ -914,31 +437,6 @@ memstore:
        return 0;
 
 out:
-       if (fwd_write_request) {
-               rzs_stat64_inc(rzs, &rzs->stats.bdev_num_writes);
-               bio->bi_bdev = rzs->backing_swap;
-#if 0
-               /*
-                * TODO: We currently have linear mapping of ramzswap and
-                * backing swap sectors. This is not desired since we want
-                * to optimize writes to backing swap to minimize disk seeks
-                * or have effective wear leveling (for SSDs). Also, a
-                * non-linear mapping is required to implement compressed
-                * on-disk swapping.
-                */
-                bio->bi_sector = get_backing_swap_page()
-                                       << SECTORS_PER_PAGE_SHIFT;
-#endif
-               /*
-                * In case backing swap is a file, find the right offset within
-                * the file corresponding to logical position 'index'. For block
-                * device, this is a nop.
-                */
-               bio->bi_sector = map_backing_swap_page(rzs, index)
-                                       << SECTORS_PER_PAGE_SHIFT;
-               return 1;
-       }
-
        bio_io_error(bio);
        return 0;
 }
@@ -996,19 +494,11 @@ static int ramzswap_make_request(struct request_queue *queue, struct bio *bio)
 
 static void reset_device(struct ramzswap *rzs)
 {
-       int is_backing_blkdev = 0;
-       size_t index, num_pages;
-       unsigned entries_per_page;
-       unsigned long num_table_pages, entry = 0;
+       size_t index;
 
        /* Do not accept any new I/O request */
        rzs->init_done = 0;
 
-       if (rzs->backing_swap && !rzs->num_extents)
-               is_backing_blkdev = 1;
-
-       num_pages = rzs->disksize >> PAGE_SHIFT;
-
        /* Free various per-device buffers */
        kfree(rzs->compress_workmem);
        free_pages((unsigned long)rzs->compress_buffer, 1);
@@ -1017,7 +507,7 @@ static void reset_device(struct ramzswap *rzs)
        rzs->compress_buffer = NULL;
 
        /* Free all pages that are still in this ramzswap device */
-       for (index = 0; index < num_pages; index++) {
+       for (index = 0; index < rzs->disksize >> PAGE_SHIFT; index++) {
                struct page *page;
                u16 offset;
 
@@ -1033,51 +523,16 @@ static void reset_device(struct ramzswap *rzs)
                        xv_free(rzs->mem_pool, page, offset);
        }
 
-       entries_per_page = PAGE_SIZE / sizeof(*rzs->table);
-       num_table_pages = DIV_ROUND_UP(num_pages * sizeof(*rzs->table),
-                                       PAGE_SIZE);
-       /*
-        * Set page->mapping to NULL for every table page.
-        * Otherwise, we will hit bad_page() during free.
-        */
-       while (rzs->num_extents && num_table_pages--) {
-               struct page *page;
-               page = vmalloc_to_page(&rzs->table[entry]);
-               page->mapping = NULL;
-               entry += entries_per_page;
-       }
        vfree(rzs->table);
        rzs->table = NULL;
 
        xv_destroy_pool(rzs->mem_pool);
        rzs->mem_pool = NULL;
 
-       /* Free all swap extent pages */
-       while (!list_empty(&rzs->backing_swap_extent_list)) {
-               struct page *page;
-               struct list_head *entry;
-               entry = rzs->backing_swap_extent_list.next;
-               page = list_entry(entry, struct page, lru);
-               list_del(entry);
-               __free_page(page);
-       }
-       INIT_LIST_HEAD(&rzs->backing_swap_extent_list);
-       rzs->num_extents = 0;
-
-       /* Close backing swap device, if present */
-       if (rzs->backing_swap) {
-               if (is_backing_blkdev)
-                       bd_release(rzs->backing_swap);
-               filp_close(rzs->swap_file, NULL);
-               rzs->backing_swap = NULL;
-               memset(rzs->backing_swap_name, 0, MAX_SWAP_NAME_LEN);
-       }
-
        /* Reset stats */
        memset(&rzs->stats, 0, sizeof(rzs->stats));
 
        rzs->disksize = 0;
-       rzs->memlimit = 0;
 }
 
 static int ramzswap_ioctl_init_device(struct ramzswap *rzs)
@@ -1092,14 +547,7 @@ static int ramzswap_ioctl_init_device(struct ramzswap *rzs)
                return -EBUSY;
        }
 
-       ret = setup_backing_swap(rzs);
-       if (ret)
-               goto fail;
-
-       if (rzs->backing_swap)
-               ramzswap_set_memlimit(rzs, totalram_pages << PAGE_SHIFT);
-       else
-               ramzswap_set_disksize(rzs, totalram_pages << PAGE_SHIFT);
+       ramzswap_set_disksize(rzs, totalram_pages << PAGE_SHIFT);
 
        rzs->compress_workmem = kzalloc(LZO1X_MEM_COMPRESS, GFP_KERNEL);
        if (!rzs->compress_workmem) {
@@ -1126,8 +574,6 @@ static int ramzswap_ioctl_init_device(struct ramzswap *rzs)
        }
        memset(rzs->table, 0, num_pages * sizeof(*rzs->table));
 
-       map_backing_swap_extents(rzs);
-
        page = alloc_page(__GFP_ZERO);
        if (!page) {
                pr_err("Error allocating swap header page\n");
@@ -1138,23 +584,13 @@ static int ramzswap_ioctl_init_device(struct ramzswap *rzs)
        rzs_set_flag(rzs, 0, RZS_UNCOMPRESSED);
 
        swap_header = kmap(page);
-       ret = setup_swap_header(rzs, swap_header);
+       setup_swap_header(rzs, swap_header);
        kunmap(page);
-       if (ret) {
-               pr_err("Error setting swap header\n");
-               goto fail;
-       }
 
        set_capacity(rzs->disk, rzs->disksize >> SECTOR_SHIFT);
 
-       /*
-        * We have ident mapping of sectors for ramzswap and
-        * and the backing swap device. So, this queue flag
-        * should be according to backing dev.
-        */
-       if (!rzs->backing_swap ||
-                       blk_queue_nonrot(rzs->backing_swap->bd_disk->queue))
-               queue_flag_set_unlocked(QUEUE_FLAG_NONROT, rzs->disk->queue);
+       /* ramzswap devices sort of resembles non-rotational disks */
+       queue_flag_set_unlocked(QUEUE_FLAG_NONROT, rzs->disk->queue);
 
        rzs->mem_pool = xv_create_pool();
        if (!rzs->mem_pool) {
@@ -1163,17 +599,6 @@ static int ramzswap_ioctl_init_device(struct ramzswap *rzs)
                goto fail;
        }
 
-       /*
-        * Pages that compress to size greater than this are forwarded
-        * to physical swap disk (if backing dev is provided)
-        * TODO: make this configurable
-        */
-       if (rzs->backing_swap)
-               max_zpage_size = max_zpage_size_bdev;
-       else
-               max_zpage_size = max_zpage_size_nobdev;
-       pr_debug("Max compressed page size: %u bytes\n", max_zpage_size);
-
        rzs->init_done = 1;
 
        pr_debug("Initialization done!\n");
@@ -1198,7 +623,7 @@ static int ramzswap_ioctl(struct block_device *bdev, fmode_t mode,
                        unsigned int cmd, unsigned long arg)
 {
        int ret = 0;
-       size_t disksize_kb, memlimit_kb;
+       size_t disksize_kb;
 
        struct ramzswap *rzs = bdev->bd_disk->private_data;
 
@@ -1217,36 +642,6 @@ static int ramzswap_ioctl(struct block_device *bdev, fmode_t mode,
                pr_info("Disk size set to %zu kB\n", disksize_kb);
                break;
 
-       case RZSIO_SET_MEMLIMIT_KB:
-               if (rzs->init_done) {
-                       /* TODO: allow changing memlimit */
-                       ret = -EBUSY;
-                       goto out;
-               }
-               if (copy_from_user(&memlimit_kb, (void *)arg,
-                                               _IOC_SIZE(cmd))) {
-                       ret = -EFAULT;
-                       goto out;
-               }
-               rzs->memlimit = memlimit_kb << 10;
-               pr_info("Memory limit set to %zu kB\n", memlimit_kb);
-               break;
-
-       case RZSIO_SET_BACKING_SWAP:
-               if (rzs->init_done) {
-                       ret = -EBUSY;
-                       goto out;
-               }
-
-               if (copy_from_user(&rzs->backing_swap_name, (void *)arg,
-                                               _IOC_SIZE(cmd))) {
-                       ret = -EFAULT;
-                       goto out;
-               }
-               rzs->backing_swap_name[MAX_SWAP_NAME_LEN - 1] = '\0';
-               pr_info("Backing swap set to %s\n", rzs->backing_swap_name);
-               break;
-
        case RZSIO_GET_STATS:
        {
                struct ramzswap_ioctl_stats *stats;
@@ -1306,7 +701,6 @@ static int create_device(struct ramzswap *rzs, int device_id)
 
        mutex_init(&rzs->lock);
        spin_lock_init(&rzs->stat64_lock);
-       INIT_LIST_HEAD(&rzs->backing_swap_extent_list);
 
        rzs->queue = blk_alloc_queue(GFP_KERNEL);
        if (!rzs->queue) {
@@ -1336,10 +730,7 @@ static int create_device(struct ramzswap *rzs, int device_id)
        rzs->disk->private_data = rzs;
        snprintf(rzs->disk->disk_name, 16, "ramzswap%d", device_id);
 
-       /*
-        * Actual capacity set using RZSIO_SET_DISKSIZE_KB ioctl
-        * or set equal to backing swap device (if provided)
-        */
+       /* Actual capacity set using RZSIO_SET_DISKSIZE_KB ioctl */
        set_capacity(rzs->disk, 0);
 
        blk_queue_physical_block_size(rzs->disk->queue, PAGE_SIZE);
index c7e0e76..63c3042 100644 (file)
@@ -31,8 +31,7 @@ static const unsigned max_num_devices = 32;
  * Stored at beginning of each compressed object.
  *
  * It stores back-reference to table entry which points to this
- * object. This is required to support memory defragmentation or
- * migrating compressed pages to backing swap disk.
+ * object. This is required to support memory defragmentation.
  */
 struct zobj_header {
 #if 0
@@ -44,27 +43,17 @@ struct zobj_header {
 
 /* Default ramzswap disk size: 25% of total RAM */
 static const unsigned default_disksize_perc_ram = 25;
-static const unsigned default_memlimit_perc_ram = 15;
 
 /*
- * Max compressed page size when backing device is provided.
- * Pages that compress to size greater than this are sent to
- * physical swap disk.
- */
-static const unsigned max_zpage_size_bdev = PAGE_SIZE / 2;
-
-/*
- * Max compressed page size when there is no backing dev.
  * Pages that compress to size greater than this are stored
  * uncompressed in memory.
  */
-static const unsigned max_zpage_size_nobdev = PAGE_SIZE / 4 * 3;
+static const unsigned max_zpage_size = PAGE_SIZE / 4 * 3;
 
 /*
- * NOTE: max_zpage_size_{bdev,nobdev} sizes must be
- * less than or equal to:
+ * NOTE: max_zpage_size must be less than or equal to:
  *   XV_MAX_ALLOC_SIZE - sizeof(struct zobj_header)
- * since otherwise xv_malloc would always return failure.
+ * otherwise, xv_malloc() would always return failure.
  */
 
 /*-- End of configurable params */
@@ -98,15 +87,6 @@ struct table {
        u8 flags;
 } __attribute__((aligned(4)));
 
-/*
- * Swap extent information in case backing swap is a regular
- * file. These extent entries must fit exactly in a page.
- */
-struct ramzswap_backing_extent {
-       pgoff_t phy_pagenum;
-       pgoff_t num_pages;
-} __attribute__((aligned(4)));
-
 struct ramzswap_stats {
        /* basic stats */
        size_t compr_size;      /* compressed size of pages stored -
@@ -123,8 +103,6 @@ struct ramzswap_stats {
        u32 pages_stored;       /* no. of pages currently stored */
        u32 good_compress;      /* % of pages with compression ratio<=50% */
        u32 pages_expand;       /* % of incompressible pages */
-       u64 bdev_num_reads;     /* no. of reads on backing dev */
-       u64 bdev_num_writes;    /* no. of writes on backing dev */
 #endif
 };
 
@@ -139,11 +117,6 @@ struct ramzswap {
        struct gendisk *disk;
        int init_done;
        /*
-        * This is limit on compressed data size (stats.compr_size)
-        * Its applicable only when backing swap device is present.
-        */
-       size_t memlimit;        /* bytes */
-       /*
         * This is limit on amount of *uncompressed* worth of data
         * we can hold. When backing swap device is provided, it is
         * set equal to device size.
@@ -151,14 +124,6 @@ struct ramzswap {
        size_t disksize;        /* bytes */
 
        struct ramzswap_stats stats;
-
-       /* backing swap device info */
-       struct ramzswap_backing_extent *curr_extent;
-       struct list_head backing_swap_extent_list;
-       unsigned long num_extents;
-       char backing_swap_name[MAX_SWAP_NAME_LEN];
-       struct block_device *backing_swap;
-       struct file *swap_file;
 };
 
 /*-- */
@@ -182,13 +147,6 @@ static void rzs_stat64_inc(struct ramzswap *rzs, u64 *v)
        spin_unlock(&rzs->stat64_lock);
 }
 
-static void rzs_stat64_dec(struct ramzswap *rzs, u64 *v)
-{
-       spin_lock(&rzs->stat64_lock);
-       *v = *v - 1;
-       spin_unlock(&rzs->stat64_lock);
-}
-
 static u64 rzs_stat64_read(struct ramzswap *rzs, u64 *v)
 {
        u64 val;
@@ -203,7 +161,6 @@ static u64 rzs_stat64_read(struct ramzswap *rzs, u64 *v)
 #define rzs_stat_inc(v)
 #define rzs_stat_dec(v)
 #define rzs_stat64_inc(r, v)
-#define rzs_stat64_dec(r, v)
 #define rzs_stat64_read(r, v)
 #endif /* CONFIG_RAMZSWAP_STATS */
 
index d26076d..db94bcb 100644 (file)
 #ifndef _RAMZSWAP_IOCTL_H_
 #define _RAMZSWAP_IOCTL_H_
 
-#define MAX_SWAP_NAME_LEN 128
-
 struct ramzswap_ioctl_stats {
-       char backing_swap_name[MAX_SWAP_NAME_LEN];
-       u64 memlimit;           /* only applicable if backing swap present */
        u64 disksize;           /* user specified or equal to backing swap
                                 * size (if present) */
        u64 num_reads;          /* failed + successful */
@@ -36,15 +32,11 @@ struct ramzswap_ioctl_stats {
        u64 orig_data_size;
        u64 compr_data_size;
        u64 mem_used_total;
-       u64 bdev_num_reads;     /* no. of reads on backing dev */
-       u64 bdev_num_writes;    /* no. of writes on backing dev */
 } __attribute__ ((packed, aligned(4)));
 
 #define RZSIO_SET_DISKSIZE_KB  _IOW('z', 0, size_t)
-#define RZSIO_SET_MEMLIMIT_KB  _IOW('z', 1, size_t)
-#define RZSIO_SET_BACKING_SWAP _IOW('z', 2, unsigned char[MAX_SWAP_NAME_LEN])
-#define RZSIO_GET_STATS                _IOR('z', 3, struct ramzswap_ioctl_stats)
-#define RZSIO_INIT             _IO('z', 4)
-#define RZSIO_RESET            _IO('z', 5)
+#define RZSIO_GET_STATS                _IOR('z', 1, struct ramzswap_ioctl_stats)
+#define RZSIO_INIT             _IO('z', 2)
+#define RZSIO_RESET            _IO('z', 3)
 
 #endif