aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorFUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>2008-07-16 14:33:35 -0400
committerBartlomiej Zolnierkiewicz <bzolnier@gmail.com>2008-07-16 14:33:35 -0400
commit0b6abc17700a7843b165c677da0ac94522f83083 (patch)
treec347a4a03941731e4df26196fb52feb7492fac23 /drivers
parent84e0f3f6c1e26588fdcb9f1b0f99d0275229bc99 (diff)
ide: avoid DMA on the stack for REQ_TYPE_ATA_PC
Some REQ_TYPE_ATA_PC commands uses the stack buffers for DMA, which leads to memory corruption on a non-coherent platform. With regard to alignment and padding, ide-cd has the the dma safe check for sg requests and REQ_TYPE_ATA_PC. This adds the stack buffer check to that check. Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> Acked-by: Borislav Petkov <petkovbb@gmail.com> Cc: Thomas Bogendoerfer <tsbogend@alpha.franken.de> Cc: Tejun Heo <htejun@gmail.com> Cc: Jens Axboe <jens.axboe@oracle.com> Cc: James Bottomley <James.Bottomley@HansenPartnership.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/ide/ide-cd.c5
1 files changed, 5 insertions, 0 deletions
diff --git a/drivers/ide/ide-cd.c b/drivers/ide/ide-cd.c
index d99847157186..d6667c36568c 100644
--- a/drivers/ide/ide-cd.c
+++ b/drivers/ide/ide-cd.c
@@ -1195,6 +1195,7 @@ static ide_startstop_t cdrom_do_block_pc(ide_drive_t *drive, struct request *rq)
1195 int mask = drive->queue->dma_alignment; 1195 int mask = drive->queue->dma_alignment;
1196 unsigned long addr = 1196 unsigned long addr =
1197 (unsigned long)page_address(bio_page(rq->bio)); 1197 (unsigned long)page_address(bio_page(rq->bio));
1198 unsigned long stack_mask = ~(THREAD_SIZE - 1);
1198 1199
1199 info->dma = drive->using_dma; 1200 info->dma = drive->using_dma;
1200 1201
@@ -1206,6 +1207,10 @@ static ide_startstop_t cdrom_do_block_pc(ide_drive_t *drive, struct request *rq)
1206 */ 1207 */
1207 if ((rq->data_len & 15) || (addr & mask)) 1208 if ((rq->data_len & 15) || (addr & mask))
1208 info->dma = 0; 1209 info->dma = 0;
1210
1211 if (!((addr & stack_mask) ^
1212 ((unsigned long)current->stack & stack_mask)))
1213 info->dma = 0;
1209 } 1214 }
1210 1215
1211 /* start sending the command to the drive */ 1216 /* start sending the command to the drive */