Skip to content

Commit

Permalink
mm: allow for outstanding swap writeback accounting
Browse files Browse the repository at this point in the history
To prevent flooding the swap device with writebacks, frontswap backends
need to count and limit the number of outstanding writebacks.  The
incrementing of the counter can be done before the call to
__swap_writepage().  However, the caller must receive a notification
when the writeback completes in order to decrement the counter.

To achieve this functionality, this patch modifies __swap_writepage() to
take the bio completion callback function as an argument.

end_swap_bio_write(), the normal bio completion function, is also made
non-static so that code doing the accounting can call it after the
accounting is done.

There should be no behavioural change to existing code.

Signed-off-by: Seth Jennings <sjenning@linux.vnet.ibm.com>
Signed-off-by: Bob Liu <bob.liu@oracle.com>
Acked-by: Minchan Kim <minchan@kernel.org>
Reviewed-by: Dan Magenheimer <dan.magenheimer@oracle.com>
Cc: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
  • Loading branch information
Seth Jennings authored and Linus Torvalds committed Apr 29, 2013
1 parent 2f772e6 commit 1eec670
Show file tree
Hide file tree
Showing 2 changed files with 8 additions and 5 deletions.
4 changes: 3 additions & 1 deletion include/linux/swap.h
Original file line number Diff line number Diff line change
Expand Up @@ -330,7 +330,9 @@ static inline void mem_cgroup_uncharge_swap(swp_entry_t ent)
/* linux/mm/page_io.c */
extern int swap_readpage(struct page *);
extern int swap_writepage(struct page *page, struct writeback_control *wbc);
extern int __swap_writepage(struct page *page, struct writeback_control *wbc);
extern void end_swap_bio_write(struct bio *bio, int err);
extern int __swap_writepage(struct page *page, struct writeback_control *wbc,
void (*end_write_func)(struct bio *, int));
extern int swap_set_page_dirty(struct page *page);
extern void end_swap_bio_read(struct bio *bio, int err);

Expand Down
9 changes: 5 additions & 4 deletions mm/page_io.c
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ static struct bio *get_swap_bio(gfp_t gfp_flags,
return bio;
}

static void end_swap_bio_write(struct bio *bio, int err)
void end_swap_bio_write(struct bio *bio, int err)
{
const int uptodate = test_bit(BIO_UPTODATE, &bio->bi_flags);
struct page *page = bio->bi_io_vec[0].bv_page;
Expand Down Expand Up @@ -197,12 +197,13 @@ int swap_writepage(struct page *page, struct writeback_control *wbc)
end_page_writeback(page);
goto out;
}
ret = __swap_writepage(page, wbc);
ret = __swap_writepage(page, wbc, end_swap_bio_write);
out:
return ret;
}

int __swap_writepage(struct page *page, struct writeback_control *wbc)
int __swap_writepage(struct page *page, struct writeback_control *wbc,
void (*end_write_func)(struct bio *, int))
{
struct bio *bio;
int ret = 0, rw = WRITE;
Expand Down Expand Up @@ -234,7 +235,7 @@ int __swap_writepage(struct page *page, struct writeback_control *wbc)
return ret;
}

bio = get_swap_bio(GFP_NOIO, page, end_swap_bio_write);
bio = get_swap_bio(GFP_NOIO, page, end_write_func);
if (bio == NULL) {
set_page_dirty(page);
unlock_page(page);
Expand Down

0 comments on commit 1eec670

Please sign in to comment.