aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRoland Dreier <rolandd@cisco.com>2008-06-10 15:29:49 -0400
committerRoland Dreier <rolandd@cisco.com>2008-06-10 15:29:49 -0400
commit24797a344293601f14f49e2d259c3ca447c4f802 (patch)
treecab0bcd13e61696ddda726ded59bd5428f72bd56
parent5e70b7f3c24468bb1635b295945edb48ecd9656a (diff)
RDMA/nes: Fix off-by-one in nes_reg_user_mr() error path
nes_reg_user_mr() should fail if page_count becomes >= 1024 * 512 rather than just testing for strict >, because page_count is essentially used as an index into an array with 1024 * 512 entries, so allowing the loop to continue with page_count == 1024 * 512 means that memory after the end of the array is corrupted. This leads to a crash triggerable by a userspace application that requests registration of a too-big region. Also get rid of the call to pci_free_consistent() here to avoid corrupting state with a double free, since the same memory will be freed in the code jumped to at reg_user_mr_err. Signed-off-by: Roland Dreier <rolandd@cisco.com>
-rw-r--r--drivers/infiniband/hw/nes/nes_verbs.c4
1 files changed, 1 insertions, 3 deletions
diff --git a/drivers/infiniband/hw/nes/nes_verbs.c b/drivers/infiniband/hw/nes/nes_verbs.c
index 99b3c4ae86eb..d617da9bd351 100644
--- a/drivers/infiniband/hw/nes/nes_verbs.c
+++ b/drivers/infiniband/hw/nes/nes_verbs.c
@@ -2456,10 +2456,8 @@ static struct ib_mr *nes_reg_user_mr(struct ib_pd *pd, u64 start, u64 length,
2456 if ((page_count!=0)&&(page_count<<12)-(region->offset&(4096-1))>=region->length) 2456 if ((page_count!=0)&&(page_count<<12)-(region->offset&(4096-1))>=region->length)
2457 goto enough_pages; 2457 goto enough_pages;
2458 if ((page_count&0x01FF) == 0) { 2458 if ((page_count&0x01FF) == 0) {
2459 if (page_count>(1024*512)) { 2459 if (page_count >= 1024 * 512) {
2460 ib_umem_release(region); 2460 ib_umem_release(region);
2461 pci_free_consistent(nesdev->pcidev, 4096, vpbl.pbl_vbase,
2462 vpbl.pbl_pbase);
2463 nes_free_resource(nesadapter, 2461 nes_free_resource(nesadapter,
2464 nesadapter->allocated_mrs, stag_index); 2462 nesadapter->allocated_mrs, stag_index);
2465 kfree(nesmr); 2463 kfree(nesmr);