]>
Commit | Line | Data |
---|---|---|
dcd32332 SL |
1 | From b98a86a12eb236bf0594ccd1ecd4b4cf333de00b Mon Sep 17 00:00:00 2001 |
2 | From: raymond pang <raymondpangxd@gmail.com> | |
3 | Date: Thu, 28 Mar 2019 12:19:25 +0000 | |
4 | Subject: libata: fix using DMA buffers on stack | |
5 | ||
6 | [ Upstream commit dd08a8d9a66de4b54575c294a92630299f7e0fe7 ] | |
7 | ||
8 | When CONFIG_VMAP_STACK=y, __pa() returns incorrect physical address for | |
9 | a stack virtual address. Stack DMA buffers must be avoided. | |
10 | ||
11 | Signed-off-by: raymond pang <raymondpangxd@gmail.com> | |
12 | Signed-off-by: Jens Axboe <axboe@kernel.dk> | |
13 | Signed-off-by: Sasha Levin (Microsoft) <sashal@kernel.org> | |
14 | --- | |
15 | drivers/ata/libata-zpodd.c | 34 ++++++++++++++++++++++++---------- | |
16 | 1 file changed, 24 insertions(+), 10 deletions(-) | |
17 | ||
18 | diff --git a/drivers/ata/libata-zpodd.c b/drivers/ata/libata-zpodd.c | |
19 | index 0ad96c647541..7017a81d53cf 100644 | |
20 | --- a/drivers/ata/libata-zpodd.c | |
21 | +++ b/drivers/ata/libata-zpodd.c | |
22 | @@ -51,38 +51,52 @@ static int eject_tray(struct ata_device *dev) | |
23 | /* Per the spec, only slot type and drawer type ODD can be supported */ | |
24 | static enum odd_mech_type zpodd_get_mech_type(struct ata_device *dev) | |
25 | { | |
26 | - char buf[16]; | |
27 | + char *buf; | |
28 | unsigned int ret; | |
29 | - struct rm_feature_desc *desc = (void *)(buf + 8); | |
30 | + struct rm_feature_desc *desc; | |
31 | struct ata_taskfile tf; | |
32 | static const char cdb[] = { GPCMD_GET_CONFIGURATION, | |
33 | 2, /* only 1 feature descriptor requested */ | |
34 | 0, 3, /* 3, removable medium feature */ | |
35 | 0, 0, 0,/* reserved */ | |
36 | - 0, sizeof(buf), | |
37 | + 0, 16, | |
38 | 0, 0, 0, | |
39 | }; | |
40 | ||
41 | + buf = kzalloc(16, GFP_KERNEL); | |
42 | + if (!buf) | |
43 | + return ODD_MECH_TYPE_UNSUPPORTED; | |
44 | + desc = (void *)(buf + 8); | |
45 | + | |
46 | ata_tf_init(dev, &tf); | |
47 | tf.flags = ATA_TFLAG_ISADDR | ATA_TFLAG_DEVICE; | |
48 | tf.command = ATA_CMD_PACKET; | |
49 | tf.protocol = ATAPI_PROT_PIO; | |
50 | - tf.lbam = sizeof(buf); | |
51 | + tf.lbam = 16; | |
52 | ||
53 | ret = ata_exec_internal(dev, &tf, cdb, DMA_FROM_DEVICE, | |
54 | - buf, sizeof(buf), 0); | |
55 | - if (ret) | |
56 | + buf, 16, 0); | |
57 | + if (ret) { | |
58 | + kfree(buf); | |
59 | return ODD_MECH_TYPE_UNSUPPORTED; | |
60 | + } | |
61 | ||
62 | - if (be16_to_cpu(desc->feature_code) != 3) | |
63 | + if (be16_to_cpu(desc->feature_code) != 3) { | |
64 | + kfree(buf); | |
65 | return ODD_MECH_TYPE_UNSUPPORTED; | |
66 | + } | |
67 | ||
68 | - if (desc->mech_type == 0 && desc->load == 0 && desc->eject == 1) | |
69 | + if (desc->mech_type == 0 && desc->load == 0 && desc->eject == 1) { | |
70 | + kfree(buf); | |
71 | return ODD_MECH_TYPE_SLOT; | |
72 | - else if (desc->mech_type == 1 && desc->load == 0 && desc->eject == 1) | |
73 | + } else if (desc->mech_type == 1 && desc->load == 0 && | |
74 | + desc->eject == 1) { | |
75 | + kfree(buf); | |
76 | return ODD_MECH_TYPE_DRAWER; | |
77 | - else | |
78 | + } else { | |
79 | + kfree(buf); | |
80 | return ODD_MECH_TYPE_UNSUPPORTED; | |
81 | + } | |
82 | } | |
83 | ||
84 | /* Test if ODD is zero power ready by sense code */ | |
85 | -- | |
86 | 2.19.1 | |
87 |