diff options
author | Dave Airlie <airlied@redhat.com> | 2011-02-22 21:06:39 -0500 |
---|---|---|
committer | Dave Airlie <airlied@redhat.com> | 2011-02-22 21:06:39 -0500 |
commit | de1e7cd63a8ec26a3bd3740708cfd72dd76509e2 (patch) | |
tree | 52bc82a71f34e92895d22821543a2be011834505 /drivers/gpu/drm/nouveau/nouveau_sgdma.c | |
parent | 7811bddb6654337fd85837ef14c1a96a0c264745 (diff) | |
parent | 5a893fc28f0393adb7c885a871b8c59e623fd528 (diff) |
Merge branch 'stable/ttm.pci-api.v5' of git://git.kernel.org/pub/scm/linux/kernel/git/konrad/xen into drm-next
* 'stable/ttm.pci-api.v5' of git://git.kernel.org/pub/scm/linux/kernel/git/konrad/xen:
ttm: Include the 'struct dev' when using the DMA API.
nouveau/ttm/PCIe: Use dma_addr if TTM has set it.
radeon/ttm/PCIe: Use dma_addr if TTM has set it.
ttm: Expand (*populate) to support an array of DMA addresses.
ttm: Utilize the DMA API for pages that have TTM_PAGE_FLAG_DMA32 set.
ttm: Introduce a placeholder for DMA (bus) addresses.
Diffstat (limited to 'drivers/gpu/drm/nouveau/nouveau_sgdma.c')
-rw-r--r-- | drivers/gpu/drm/nouveau/nouveau_sgdma.c | 31 |
1 files changed, 23 insertions, 8 deletions
diff --git a/drivers/gpu/drm/nouveau/nouveau_sgdma.c b/drivers/gpu/drm/nouveau/nouveau_sgdma.c index 9a250eb53098..07b115184b87 100644 --- a/drivers/gpu/drm/nouveau/nouveau_sgdma.c +++ b/drivers/gpu/drm/nouveau/nouveau_sgdma.c | |||
@@ -12,6 +12,7 @@ struct nouveau_sgdma_be { | |||
12 | struct drm_device *dev; | 12 | struct drm_device *dev; |
13 | 13 | ||
14 | dma_addr_t *pages; | 14 | dma_addr_t *pages; |
15 | bool *ttm_alloced; | ||
15 | unsigned nr_pages; | 16 | unsigned nr_pages; |
16 | 17 | ||
17 | u64 offset; | 18 | u64 offset; |
@@ -20,7 +21,8 @@ struct nouveau_sgdma_be { | |||
20 | 21 | ||
21 | static int | 22 | static int |
22 | nouveau_sgdma_populate(struct ttm_backend *be, unsigned long num_pages, | 23 | nouveau_sgdma_populate(struct ttm_backend *be, unsigned long num_pages, |
23 | struct page **pages, struct page *dummy_read_page) | 24 | struct page **pages, struct page *dummy_read_page, |
25 | dma_addr_t *dma_addrs) | ||
24 | { | 26 | { |
25 | struct nouveau_sgdma_be *nvbe = (struct nouveau_sgdma_be *)be; | 27 | struct nouveau_sgdma_be *nvbe = (struct nouveau_sgdma_be *)be; |
26 | struct drm_device *dev = nvbe->dev; | 28 | struct drm_device *dev = nvbe->dev; |
@@ -34,15 +36,25 @@ nouveau_sgdma_populate(struct ttm_backend *be, unsigned long num_pages, | |||
34 | if (!nvbe->pages) | 36 | if (!nvbe->pages) |
35 | return -ENOMEM; | 37 | return -ENOMEM; |
36 | 38 | ||
39 | nvbe->ttm_alloced = kmalloc(sizeof(bool) * num_pages, GFP_KERNEL); | ||
40 | if (!nvbe->ttm_alloced) | ||
41 | return -ENOMEM; | ||
42 | |||
37 | nvbe->nr_pages = 0; | 43 | nvbe->nr_pages = 0; |
38 | while (num_pages--) { | 44 | while (num_pages--) { |
39 | nvbe->pages[nvbe->nr_pages] = | 45 | if (dma_addrs[nvbe->nr_pages] != DMA_ERROR_CODE) { |
40 | pci_map_page(dev->pdev, pages[nvbe->nr_pages], 0, | 46 | nvbe->pages[nvbe->nr_pages] = |
47 | dma_addrs[nvbe->nr_pages]; | ||
48 | nvbe->ttm_alloced[nvbe->nr_pages] = true; | ||
49 | } else { | ||
50 | nvbe->pages[nvbe->nr_pages] = | ||
51 | pci_map_page(dev->pdev, pages[nvbe->nr_pages], 0, | ||
41 | PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); | 52 | PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); |
42 | if (pci_dma_mapping_error(dev->pdev, | 53 | if (pci_dma_mapping_error(dev->pdev, |
43 | nvbe->pages[nvbe->nr_pages])) { | 54 | nvbe->pages[nvbe->nr_pages])) { |
44 | be->func->clear(be); | 55 | be->func->clear(be); |
45 | return -EFAULT; | 56 | return -EFAULT; |
57 | } | ||
46 | } | 58 | } |
47 | 59 | ||
48 | nvbe->nr_pages++; | 60 | nvbe->nr_pages++; |
@@ -65,11 +77,14 @@ nouveau_sgdma_clear(struct ttm_backend *be) | |||
65 | be->func->unbind(be); | 77 | be->func->unbind(be); |
66 | 78 | ||
67 | while (nvbe->nr_pages--) { | 79 | while (nvbe->nr_pages--) { |
68 | pci_unmap_page(dev->pdev, nvbe->pages[nvbe->nr_pages], | 80 | if (!nvbe->ttm_alloced[nvbe->nr_pages]) |
81 | pci_unmap_page(dev->pdev, nvbe->pages[nvbe->nr_pages], | ||
69 | PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); | 82 | PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); |
70 | } | 83 | } |
71 | kfree(nvbe->pages); | 84 | kfree(nvbe->pages); |
85 | kfree(nvbe->ttm_alloced); | ||
72 | nvbe->pages = NULL; | 86 | nvbe->pages = NULL; |
87 | nvbe->ttm_alloced = NULL; | ||
73 | nvbe->nr_pages = 0; | 88 | nvbe->nr_pages = 0; |
74 | } | 89 | } |
75 | } | 90 | } |