Skip to content

Commit

Permalink
iov_iter: Fix iov_iter_get_pages{,_alloc} page fault return value
Browse files Browse the repository at this point in the history
Both iov_iter_get_pages and iov_iter_get_pages_alloc return the number
of bytes of the iovec they could get the pages for.  When they cannot
get any pages, they're supposed to return 0, but when the start of the
iovec isn't page aligned, the calculation goes wrong and they return a
negative value.  Fix both functions.

In addition, change iov_iter_get_pages_alloc to return NULL in that case
to prevent resource leaks.

Signed-off-by: Andreas Gruenbacher <agruenba@redhat.com>
Reviewed-by: Christoph Hellwig <hch@lst.de>
  • Loading branch information
Andreas Gruenbacher committed Oct 12, 2021
1 parent 64570fb commit 814a667
Showing 1 changed file with 3 additions and 2 deletions.
5 changes: 3 additions & 2 deletions lib/iov_iter.c
Original file line number Diff line number Diff line change
Expand Up @@ -1488,7 +1488,7 @@ ssize_t iov_iter_get_pages(struct iov_iter *i,
res = get_user_pages_fast(addr, n,
iov_iter_rw(i) != WRITE ? FOLL_WRITE : 0,
pages);
if (unlikely(res < 0))
if (unlikely(res <= 0))
return res;
return (res == n ? len : res * PAGE_SIZE) - *start;
}
Expand Down Expand Up @@ -1612,8 +1612,9 @@ ssize_t iov_iter_get_pages_alloc(struct iov_iter *i,
return -ENOMEM;
res = get_user_pages_fast(addr, n,
iov_iter_rw(i) != WRITE ? FOLL_WRITE : 0, p);
if (unlikely(res < 0)) {
if (unlikely(res <= 0)) {
kvfree(p);
*pages = NULL;
return res;
}
*pages = p;
Expand Down

0 comments on commit 814a667

Please sign in to comment.