diff options
author | David Jeffery <djeffery@redhat.com> | 2009-09-28 13:54:24 -0400 |
---|---|---|
committer | James Bottomley <James.Bottomley@suse.de> | 2009-10-02 15:11:58 -0400 |
commit | 2c2ed8bfd899b84ecbf71d28fcc2cc4ace36c8d9 (patch) | |
tree | 890fd3916878e2427141d6e53dd70150ac7ff93e /drivers/scsi/st.c | |
parent | 2afc95bf546a961d2936d886c3802e159f1bae6b (diff) |
[SCSI] st: fix possible memory use after free after MTSETBLK ioctl
A memory use after free bug can manifest if the MTSETBLK or SET_DENS_AND_BLK
ioctl features are used to set the tape's blocksize from 0 to non-zero.
After the driver sets the new block size, in this one case it calls
normalize_buffer() to free the device's internal data buffers. However, the
ioctl code assumes there is always a buffer and does not check or allocate
a buffer if there isn't one. So any following ioctl calls can corrupt
a part of memory by writing data to memory that the st driver had freed.
This patch removes the normalize_buffer() call and the specialness of
changing from a 0 to non-zero blocksize to fix the possible use of
memory after it has been freed by the st driver.
signed-off-by: David Jeffery <djeffery@redhat.com>
Acked-by: Kai Makisara <kai.makisara@kolumbus.fi>
Signed-off-by: James Bottomley <James.Bottomley@suse.de>
Diffstat (limited to 'drivers/scsi/st.c')
-rw-r--r-- | drivers/scsi/st.c | 3 |
1 files changed, 0 insertions, 3 deletions
diff --git a/drivers/scsi/st.c b/drivers/scsi/st.c index b33d04250bbc..12d58a7ed6bc 100644 --- a/drivers/scsi/st.c +++ b/drivers/scsi/st.c | |||
@@ -2859,11 +2859,8 @@ static int st_int_ioctl(struct scsi_tape *STp, unsigned int cmd_in, unsigned lon | |||
2859 | ioctl_result = st_int_ioctl(STp, MTBSF, 1); | 2859 | ioctl_result = st_int_ioctl(STp, MTBSF, 1); |
2860 | 2860 | ||
2861 | if (cmd_in == MTSETBLK || cmd_in == SET_DENS_AND_BLK) { | 2861 | if (cmd_in == MTSETBLK || cmd_in == SET_DENS_AND_BLK) { |
2862 | int old_block_size = STp->block_size; | ||
2863 | STp->block_size = arg & MT_ST_BLKSIZE_MASK; | 2862 | STp->block_size = arg & MT_ST_BLKSIZE_MASK; |
2864 | if (STp->block_size != 0) { | 2863 | if (STp->block_size != 0) { |
2865 | if (old_block_size == 0) | ||
2866 | normalize_buffer(STp->buffer); | ||
2867 | (STp->buffer)->buffer_blocks = | 2864 | (STp->buffer)->buffer_blocks = |
2868 | (STp->buffer)->buffer_size / STp->block_size; | 2865 | (STp->buffer)->buffer_size / STp->block_size; |
2869 | } | 2866 | } |