lkml.org 
[lkml]   [2012]   [Sep]   [7]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH 02/11] target: report too-small parameter lists everywhere
    Date
    Several places were not checking that the parameter list length
    was large enough, and thus accessing invalid memory. Zero-length
    parameter lists are just a special case of this.

    Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
    ---
    drivers/target/target_core_alua.c | 7 +++++++
    drivers/target/target_core_iblock.c | 17 +++++++++++++++--
    drivers/target/target_core_pr.c | 8 ++++++++
    3 files changed, 30 insertions(+), 2 deletions(-)

    diff --git a/drivers/target/target_core_alua.c b/drivers/target/target_core_alua.c
    index 9179997..41641ba 100644
    --- a/drivers/target/target_core_alua.c
    +++ b/drivers/target/target_core_alua.c
    @@ -218,6 +218,13 @@ int target_emulate_set_target_port_groups(struct se_cmd *cmd)
    cmd->scsi_sense_reason = TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE;
    return -EINVAL;
    }
    + if (cmd->data_length < 4) {
    + pr_warn("SET TARGET PORT GROUPS parameter list length %u too"
    + " small\n", cmd->data_length);
    + cmd->scsi_sense_reason = TCM_INVALID_PARAMETER_LIST;
    + return -EINVAL;
    + }
    +
    buf = transport_kmap_data_sg(cmd);

    /*
    diff --git a/drivers/target/target_core_iblock.c b/drivers/target/target_core_iblock.c
    index 76db75e..9ba4954 100644
    --- a/drivers/target/target_core_iblock.c
    +++ b/drivers/target/target_core_iblock.c
    @@ -325,17 +325,30 @@ static int iblock_execute_unmap(struct se_cmd *cmd)
    struct iblock_dev *ibd = dev->dev_ptr;
    unsigned char *buf, *ptr = NULL;
    sector_t lba;
    - int size = cmd->data_length;
    + int size;
    u32 range;
    int ret = 0;
    int dl, bd_dl;

    + if (cmd->data_length < 8) {
    + pr_warn("UNMAP parameter list length %u too small\n",
    + cmd->data_length);
    + cmd->scsi_sense_reason = TCM_INVALID_PARAMETER_LIST;
    + return -EINVAL;
    + }
    +
    buf = transport_kmap_data_sg(cmd);

    dl = get_unaligned_be16(&buf[0]);
    bd_dl = get_unaligned_be16(&buf[2]);

    - size = min(size - 8, bd_dl);
    + size = cmd->data_length - 8;
    + if (bd_dl > size)
    + pr_warn("UNMAP parameter list length %u too small, ignoring bd_dl %u\n",
    + cmd->data_length, bd_dl);
    + else
    + size = bd_dl;
    +
    if (size / 16 > dev->se_sub_dev->se_dev_attrib.max_unmap_block_desc_count) {
    cmd->scsi_sense_reason = TCM_INVALID_PARAMETER_LIST;
    ret = -EINVAL;
    diff --git a/drivers/target/target_core_pr.c b/drivers/target/target_core_pr.c
    index 1e94650..956c84c 100644
    --- a/drivers/target/target_core_pr.c
    +++ b/drivers/target/target_core_pr.c
    @@ -1540,6 +1540,14 @@ static int core_scsi3_decode_spec_i_port(
    tidh_new->dest_local_nexus = 1;
    list_add_tail(&tidh_new->dest_list, &tid_dest_list);

    + if (cmd->data_length < 28) {
    + pr_warn("SPC-PR: Received PR OUT parameter list"
    + " length too small: %u\n", cmd->data_length);
    + cmd->scsi_sense_reason = TCM_INVALID_PARAMETER_LIST;
    + ret = -EINVAL;
    + goto out;
    + }
    +
    buf = transport_kmap_data_sg(cmd);
    /*
    * For a PERSISTENT RESERVE OUT specify initiator ports payload,
    --
    1.7.1



    \
     
     \ /
      Last update: 2012-09-07 18:41    [W:3.706 / U:0.004 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site