Skip to content

Commit

Permalink
IB/ipath: Fix possible data corruption if multiple SGEs used for receive
Browse files Browse the repository at this point in the history
The code to copy data from the receive queue buffers to the IB SGEs
doesn't check the SGE length, only the memory region/page length when
copying data.  This could overwrite parts of the user's memory that
were not intended to be written.  It can only happen if multiple SGEs
are used to describe a receive buffer which almost never happens in
practice.

Signed-off-by: Ralph Campbell <ralph.campbell@qlogic.com>
Signed-off-by: Roland Dreier <rolandd@cisco.com>
  • Loading branch information
Ralph Campbell authored and Roland Dreier committed Jul 10, 2007
1 parent db5518c commit 30d149a
Show file tree
Hide file tree
Showing 3 changed files with 10 additions and 2 deletions.
2 changes: 2 additions & 0 deletions drivers/infiniband/hw/ipath/ipath_ruc.c
Original file line number Diff line number Diff line change
Expand Up @@ -396,6 +396,8 @@ static void ipath_ruc_loopback(struct ipath_qp *sqp)

if (len > sge->length)
len = sge->length;
if (len > sge->sge_length)
len = sge->sge_length;
BUG_ON(len == 0);
ipath_copy_sge(&qp->r_sge, sge->vaddr, len);
sge->vaddr += len;
Expand Down
2 changes: 2 additions & 0 deletions drivers/infiniband/hw/ipath/ipath_ud.c
Original file line number Diff line number Diff line change
Expand Up @@ -231,6 +231,8 @@ static void ipath_ud_loopback(struct ipath_qp *sqp,

if (len > length)
len = length;
if (len > sge->sge_length)
len = sge->sge_length;
BUG_ON(len == 0);
ipath_copy_sge(&rsge, sge->vaddr, len);
sge->vaddr += len;
Expand Down
8 changes: 6 additions & 2 deletions drivers/infiniband/hw/ipath/ipath_verbs.c
Original file line number Diff line number Diff line change
Expand Up @@ -164,9 +164,11 @@ void ipath_copy_sge(struct ipath_sge_state *ss, void *data, u32 length)
while (length) {
u32 len = sge->length;

BUG_ON(len == 0);
if (len > length)
len = length;
if (len > sge->sge_length)
len = sge->sge_length;
BUG_ON(len == 0);
memcpy(sge->vaddr, data, len);
sge->vaddr += len;
sge->length -= len;
Expand Down Expand Up @@ -202,9 +204,11 @@ void ipath_skip_sge(struct ipath_sge_state *ss, u32 length)
while (length) {
u32 len = sge->length;

BUG_ON(len == 0);
if (len > length)
len = length;
if (len > sge->sge_length)
len = sge->sge_length;
BUG_ON(len == 0);
sge->vaddr += len;
sge->length -= len;
sge->sge_length -= len;
Expand Down

0 comments on commit 30d149a

Please sign in to comment.