]> git.ipfire.org Git - thirdparty/kernel/stable-queue.git/blob - releases/3.4.75/alsa-memalloc.h-fix-wrong-truncation-of-dma_addr_t.patch
Linux 4.14.95
[thirdparty/kernel/stable-queue.git] / releases / 3.4.75 / alsa-memalloc.h-fix-wrong-truncation-of-dma_addr_t.patch
1 From 932e9dec380c67ec15ac3eb073bb55797d8b4801 Mon Sep 17 00:00:00 2001
2 From: Stefano Panella <stefano.panella@citrix.com>
3 Date: Tue, 10 Dec 2013 14:20:28 +0000
4 Subject: ALSA: memalloc.h - fix wrong truncation of dma_addr_t
5
6 From: Stefano Panella <stefano.panella@citrix.com>
7
8 commit 932e9dec380c67ec15ac3eb073bb55797d8b4801 upstream.
9
10 When running a 32bit kernel the hda_intel driver is still reporting
11 a 64bit dma_mask if the HW supports it.
12
13 From sound/pci/hda/hda_intel.c:
14
15 /* allow 64bit DMA address if supported by H/W */
16 if ((gcap & ICH6_GCAP_64OK) && !pci_set_dma_mask(pci, DMA_BIT_MASK(64)))
17 pci_set_consistent_dma_mask(pci, DMA_BIT_MASK(64));
18 else {
19 pci_set_dma_mask(pci, DMA_BIT_MASK(32));
20 pci_set_consistent_dma_mask(pci, DMA_BIT_MASK(32));
21 }
22
23 which means when there is a call to dma_alloc_coherent from
24 snd_malloc_dev_pages a machine address bigger than 32bit can be returned.
25 This can be true in particular if running the 32bit kernel as a pv dom0
26 under the Xen Hypervisor or PAE on bare metal.
27
28 The problem is that when calling setup_bdle to program the BLE the
29 dma_addr_t returned from the dma_alloc_coherent is wrongly truncated
30 from snd_sgbuf_get_addr if running a 32bit kernel:
31
32 static inline dma_addr_t snd_sgbuf_get_addr(struct snd_dma_buffer *dmab,
33 size_t offset)
34 {
35 struct snd_sg_buf *sgbuf = dmab->private_data;
36 dma_addr_t addr = sgbuf->table[offset >> PAGE_SHIFT].addr;
37 addr &= PAGE_MASK;
38 return addr + offset % PAGE_SIZE;
39 }
40
41 where PAGE_MASK in a 32bit kernel is zeroing the upper 32bit af addr.
42
43 Without this patch the HW will fetch the 32bit truncated address,
44 which is not the one obtained from dma_alloc_coherent and will result
45 to a non working audio but can corrupt host memory at a random location.
46
47 The current patch apply to v3.13-rc3-74-g6c843f5
48
49 Signed-off-by: Stefano Panella <stefano.panella@citrix.com>
50 Reviewed-by: Frediano Ziglio <frediano.ziglio@citrix.com>
51 Signed-off-by: Takashi Iwai <tiwai@suse.de>
52 Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
53
54 ---
55 include/sound/memalloc.h | 2 +-
56 1 file changed, 1 insertion(+), 1 deletion(-)
57
58 --- a/include/sound/memalloc.h
59 +++ b/include/sound/memalloc.h
60 @@ -101,7 +101,7 @@ static inline unsigned int snd_sgbuf_ali
61 static inline dma_addr_t snd_sgbuf_get_addr(struct snd_sg_buf *sgbuf, size_t offset)
62 {
63 dma_addr_t addr = sgbuf->table[offset >> PAGE_SHIFT].addr;
64 - addr &= PAGE_MASK;
65 + addr &= ~((dma_addr_t)PAGE_SIZE - 1);
66 return addr + offset % PAGE_SIZE;
67 }
68