1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun * linux/arch/alpha/kernel/pci_iommu.c
4*4882a593Smuzhiyun */
5*4882a593Smuzhiyun
6*4882a593Smuzhiyun #include <linux/kernel.h>
7*4882a593Smuzhiyun #include <linux/mm.h>
8*4882a593Smuzhiyun #include <linux/pci.h>
9*4882a593Smuzhiyun #include <linux/gfp.h>
10*4882a593Smuzhiyun #include <linux/memblock.h>
11*4882a593Smuzhiyun #include <linux/export.h>
12*4882a593Smuzhiyun #include <linux/scatterlist.h>
13*4882a593Smuzhiyun #include <linux/log2.h>
14*4882a593Smuzhiyun #include <linux/dma-map-ops.h>
15*4882a593Smuzhiyun #include <linux/iommu-helper.h>
16*4882a593Smuzhiyun
17*4882a593Smuzhiyun #include <asm/io.h>
18*4882a593Smuzhiyun #include <asm/hwrpb.h>
19*4882a593Smuzhiyun
20*4882a593Smuzhiyun #include "proto.h"
21*4882a593Smuzhiyun #include "pci_impl.h"
22*4882a593Smuzhiyun
23*4882a593Smuzhiyun
24*4882a593Smuzhiyun #define DEBUG_ALLOC 0
25*4882a593Smuzhiyun #if DEBUG_ALLOC > 0
26*4882a593Smuzhiyun # define DBGA(args...) printk(KERN_DEBUG args)
27*4882a593Smuzhiyun #else
28*4882a593Smuzhiyun # define DBGA(args...)
29*4882a593Smuzhiyun #endif
30*4882a593Smuzhiyun #if DEBUG_ALLOC > 1
31*4882a593Smuzhiyun # define DBGA2(args...) printk(KERN_DEBUG args)
32*4882a593Smuzhiyun #else
33*4882a593Smuzhiyun # define DBGA2(args...)
34*4882a593Smuzhiyun #endif
35*4882a593Smuzhiyun
36*4882a593Smuzhiyun #define DEBUG_NODIRECT 0
37*4882a593Smuzhiyun
38*4882a593Smuzhiyun #define ISA_DMA_MASK 0x00ffffff
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun static inline unsigned long
mk_iommu_pte(unsigned long paddr)41*4882a593Smuzhiyun mk_iommu_pte(unsigned long paddr)
42*4882a593Smuzhiyun {
43*4882a593Smuzhiyun return (paddr >> (PAGE_SHIFT-1)) | 1;
44*4882a593Smuzhiyun }
45*4882a593Smuzhiyun
46*4882a593Smuzhiyun /* Return the minimum of MAX or the first power of two larger
47*4882a593Smuzhiyun than main memory. */
48*4882a593Smuzhiyun
49*4882a593Smuzhiyun unsigned long
size_for_memory(unsigned long max)50*4882a593Smuzhiyun size_for_memory(unsigned long max)
51*4882a593Smuzhiyun {
52*4882a593Smuzhiyun unsigned long mem = max_low_pfn << PAGE_SHIFT;
53*4882a593Smuzhiyun if (mem < max)
54*4882a593Smuzhiyun max = roundup_pow_of_two(mem);
55*4882a593Smuzhiyun return max;
56*4882a593Smuzhiyun }
57*4882a593Smuzhiyun
58*4882a593Smuzhiyun struct pci_iommu_arena * __init
iommu_arena_new_node(int nid,struct pci_controller * hose,dma_addr_t base,unsigned long window_size,unsigned long align)59*4882a593Smuzhiyun iommu_arena_new_node(int nid, struct pci_controller *hose, dma_addr_t base,
60*4882a593Smuzhiyun unsigned long window_size, unsigned long align)
61*4882a593Smuzhiyun {
62*4882a593Smuzhiyun unsigned long mem_size;
63*4882a593Smuzhiyun struct pci_iommu_arena *arena;
64*4882a593Smuzhiyun
65*4882a593Smuzhiyun mem_size = window_size / (PAGE_SIZE / sizeof(unsigned long));
66*4882a593Smuzhiyun
67*4882a593Smuzhiyun /* Note that the TLB lookup logic uses bitwise concatenation,
68*4882a593Smuzhiyun not addition, so the required arena alignment is based on
69*4882a593Smuzhiyun the size of the window. Retain the align parameter so that
70*4882a593Smuzhiyun particular systems can over-align the arena. */
71*4882a593Smuzhiyun if (align < mem_size)
72*4882a593Smuzhiyun align = mem_size;
73*4882a593Smuzhiyun
74*4882a593Smuzhiyun
75*4882a593Smuzhiyun #ifdef CONFIG_DISCONTIGMEM
76*4882a593Smuzhiyun
77*4882a593Smuzhiyun arena = memblock_alloc_node(sizeof(*arena), align, nid);
78*4882a593Smuzhiyun if (!NODE_DATA(nid) || !arena) {
79*4882a593Smuzhiyun printk("%s: couldn't allocate arena from node %d\n"
80*4882a593Smuzhiyun " falling back to system-wide allocation\n",
81*4882a593Smuzhiyun __func__, nid);
82*4882a593Smuzhiyun arena = memblock_alloc(sizeof(*arena), SMP_CACHE_BYTES);
83*4882a593Smuzhiyun if (!arena)
84*4882a593Smuzhiyun panic("%s: Failed to allocate %zu bytes\n", __func__,
85*4882a593Smuzhiyun sizeof(*arena));
86*4882a593Smuzhiyun }
87*4882a593Smuzhiyun
88*4882a593Smuzhiyun arena->ptes = memblock_alloc_node(sizeof(*arena), align, nid);
89*4882a593Smuzhiyun if (!NODE_DATA(nid) || !arena->ptes) {
90*4882a593Smuzhiyun printk("%s: couldn't allocate arena ptes from node %d\n"
91*4882a593Smuzhiyun " falling back to system-wide allocation\n",
92*4882a593Smuzhiyun __func__, nid);
93*4882a593Smuzhiyun arena->ptes = memblock_alloc(mem_size, align);
94*4882a593Smuzhiyun if (!arena->ptes)
95*4882a593Smuzhiyun panic("%s: Failed to allocate %lu bytes align=0x%lx\n",
96*4882a593Smuzhiyun __func__, mem_size, align);
97*4882a593Smuzhiyun }
98*4882a593Smuzhiyun
99*4882a593Smuzhiyun #else /* CONFIG_DISCONTIGMEM */
100*4882a593Smuzhiyun
101*4882a593Smuzhiyun arena = memblock_alloc(sizeof(*arena), SMP_CACHE_BYTES);
102*4882a593Smuzhiyun if (!arena)
103*4882a593Smuzhiyun panic("%s: Failed to allocate %zu bytes\n", __func__,
104*4882a593Smuzhiyun sizeof(*arena));
105*4882a593Smuzhiyun arena->ptes = memblock_alloc(mem_size, align);
106*4882a593Smuzhiyun if (!arena->ptes)
107*4882a593Smuzhiyun panic("%s: Failed to allocate %lu bytes align=0x%lx\n",
108*4882a593Smuzhiyun __func__, mem_size, align);
109*4882a593Smuzhiyun
110*4882a593Smuzhiyun #endif /* CONFIG_DISCONTIGMEM */
111*4882a593Smuzhiyun
112*4882a593Smuzhiyun spin_lock_init(&arena->lock);
113*4882a593Smuzhiyun arena->hose = hose;
114*4882a593Smuzhiyun arena->dma_base = base;
115*4882a593Smuzhiyun arena->size = window_size;
116*4882a593Smuzhiyun arena->next_entry = 0;
117*4882a593Smuzhiyun
118*4882a593Smuzhiyun /* Align allocations to a multiple of a page size. Not needed
119*4882a593Smuzhiyun unless there are chip bugs. */
120*4882a593Smuzhiyun arena->align_entry = 1;
121*4882a593Smuzhiyun
122*4882a593Smuzhiyun return arena;
123*4882a593Smuzhiyun }
124*4882a593Smuzhiyun
125*4882a593Smuzhiyun struct pci_iommu_arena * __init
iommu_arena_new(struct pci_controller * hose,dma_addr_t base,unsigned long window_size,unsigned long align)126*4882a593Smuzhiyun iommu_arena_new(struct pci_controller *hose, dma_addr_t base,
127*4882a593Smuzhiyun unsigned long window_size, unsigned long align)
128*4882a593Smuzhiyun {
129*4882a593Smuzhiyun return iommu_arena_new_node(0, hose, base, window_size, align);
130*4882a593Smuzhiyun }
131*4882a593Smuzhiyun
132*4882a593Smuzhiyun /* Must be called with the arena lock held */
133*4882a593Smuzhiyun static long
iommu_arena_find_pages(struct device * dev,struct pci_iommu_arena * arena,long n,long mask)134*4882a593Smuzhiyun iommu_arena_find_pages(struct device *dev, struct pci_iommu_arena *arena,
135*4882a593Smuzhiyun long n, long mask)
136*4882a593Smuzhiyun {
137*4882a593Smuzhiyun unsigned long *ptes;
138*4882a593Smuzhiyun long i, p, nent;
139*4882a593Smuzhiyun int pass = 0;
140*4882a593Smuzhiyun unsigned long base;
141*4882a593Smuzhiyun unsigned long boundary_size;
142*4882a593Smuzhiyun
143*4882a593Smuzhiyun base = arena->dma_base >> PAGE_SHIFT;
144*4882a593Smuzhiyun boundary_size = dma_get_seg_boundary_nr_pages(dev, PAGE_SHIFT);
145*4882a593Smuzhiyun
146*4882a593Smuzhiyun /* Search forward for the first mask-aligned sequence of N free ptes */
147*4882a593Smuzhiyun ptes = arena->ptes;
148*4882a593Smuzhiyun nent = arena->size >> PAGE_SHIFT;
149*4882a593Smuzhiyun p = ALIGN(arena->next_entry, mask + 1);
150*4882a593Smuzhiyun i = 0;
151*4882a593Smuzhiyun
152*4882a593Smuzhiyun again:
153*4882a593Smuzhiyun while (i < n && p+i < nent) {
154*4882a593Smuzhiyun if (!i && iommu_is_span_boundary(p, n, base, boundary_size)) {
155*4882a593Smuzhiyun p = ALIGN(p + 1, mask + 1);
156*4882a593Smuzhiyun goto again;
157*4882a593Smuzhiyun }
158*4882a593Smuzhiyun
159*4882a593Smuzhiyun if (ptes[p+i])
160*4882a593Smuzhiyun p = ALIGN(p + i + 1, mask + 1), i = 0;
161*4882a593Smuzhiyun else
162*4882a593Smuzhiyun i = i + 1;
163*4882a593Smuzhiyun }
164*4882a593Smuzhiyun
165*4882a593Smuzhiyun if (i < n) {
166*4882a593Smuzhiyun if (pass < 1) {
167*4882a593Smuzhiyun /*
168*4882a593Smuzhiyun * Reached the end. Flush the TLB and restart
169*4882a593Smuzhiyun * the search from the beginning.
170*4882a593Smuzhiyun */
171*4882a593Smuzhiyun alpha_mv.mv_pci_tbi(arena->hose, 0, -1);
172*4882a593Smuzhiyun
173*4882a593Smuzhiyun pass++;
174*4882a593Smuzhiyun p = 0;
175*4882a593Smuzhiyun i = 0;
176*4882a593Smuzhiyun goto again;
177*4882a593Smuzhiyun } else
178*4882a593Smuzhiyun return -1;
179*4882a593Smuzhiyun }
180*4882a593Smuzhiyun
181*4882a593Smuzhiyun /* Success. It's the responsibility of the caller to mark them
182*4882a593Smuzhiyun in use before releasing the lock */
183*4882a593Smuzhiyun return p;
184*4882a593Smuzhiyun }
185*4882a593Smuzhiyun
186*4882a593Smuzhiyun static long
iommu_arena_alloc(struct device * dev,struct pci_iommu_arena * arena,long n,unsigned int align)187*4882a593Smuzhiyun iommu_arena_alloc(struct device *dev, struct pci_iommu_arena *arena, long n,
188*4882a593Smuzhiyun unsigned int align)
189*4882a593Smuzhiyun {
190*4882a593Smuzhiyun unsigned long flags;
191*4882a593Smuzhiyun unsigned long *ptes;
192*4882a593Smuzhiyun long i, p, mask;
193*4882a593Smuzhiyun
194*4882a593Smuzhiyun spin_lock_irqsave(&arena->lock, flags);
195*4882a593Smuzhiyun
196*4882a593Smuzhiyun /* Search for N empty ptes */
197*4882a593Smuzhiyun ptes = arena->ptes;
198*4882a593Smuzhiyun mask = max(align, arena->align_entry) - 1;
199*4882a593Smuzhiyun p = iommu_arena_find_pages(dev, arena, n, mask);
200*4882a593Smuzhiyun if (p < 0) {
201*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
202*4882a593Smuzhiyun return -1;
203*4882a593Smuzhiyun }
204*4882a593Smuzhiyun
205*4882a593Smuzhiyun /* Success. Mark them all in use, ie not zero and invalid
206*4882a593Smuzhiyun for the iommu tlb that could load them from under us.
207*4882a593Smuzhiyun The chip specific bits will fill this in with something
208*4882a593Smuzhiyun kosher when we return. */
209*4882a593Smuzhiyun for (i = 0; i < n; ++i)
210*4882a593Smuzhiyun ptes[p+i] = IOMMU_INVALID_PTE;
211*4882a593Smuzhiyun
212*4882a593Smuzhiyun arena->next_entry = p + n;
213*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
214*4882a593Smuzhiyun
215*4882a593Smuzhiyun return p;
216*4882a593Smuzhiyun }
217*4882a593Smuzhiyun
218*4882a593Smuzhiyun static void
iommu_arena_free(struct pci_iommu_arena * arena,long ofs,long n)219*4882a593Smuzhiyun iommu_arena_free(struct pci_iommu_arena *arena, long ofs, long n)
220*4882a593Smuzhiyun {
221*4882a593Smuzhiyun unsigned long *p;
222*4882a593Smuzhiyun long i;
223*4882a593Smuzhiyun
224*4882a593Smuzhiyun p = arena->ptes + ofs;
225*4882a593Smuzhiyun for (i = 0; i < n; ++i)
226*4882a593Smuzhiyun p[i] = 0;
227*4882a593Smuzhiyun }
228*4882a593Smuzhiyun
229*4882a593Smuzhiyun /*
230*4882a593Smuzhiyun * True if the machine supports DAC addressing, and DEV can
231*4882a593Smuzhiyun * make use of it given MASK.
232*4882a593Smuzhiyun */
pci_dac_dma_supported(struct pci_dev * dev,u64 mask)233*4882a593Smuzhiyun static int pci_dac_dma_supported(struct pci_dev *dev, u64 mask)
234*4882a593Smuzhiyun {
235*4882a593Smuzhiyun dma_addr_t dac_offset = alpha_mv.pci_dac_offset;
236*4882a593Smuzhiyun int ok = 1;
237*4882a593Smuzhiyun
238*4882a593Smuzhiyun /* If this is not set, the machine doesn't support DAC at all. */
239*4882a593Smuzhiyun if (dac_offset == 0)
240*4882a593Smuzhiyun ok = 0;
241*4882a593Smuzhiyun
242*4882a593Smuzhiyun /* The device has to be able to address our DAC bit. */
243*4882a593Smuzhiyun if ((dac_offset & dev->dma_mask) != dac_offset)
244*4882a593Smuzhiyun ok = 0;
245*4882a593Smuzhiyun
246*4882a593Smuzhiyun /* If both conditions above are met, we are fine. */
247*4882a593Smuzhiyun DBGA("pci_dac_dma_supported %s from %ps\n",
248*4882a593Smuzhiyun ok ? "yes" : "no", __builtin_return_address(0));
249*4882a593Smuzhiyun
250*4882a593Smuzhiyun return ok;
251*4882a593Smuzhiyun }
252*4882a593Smuzhiyun
253*4882a593Smuzhiyun /* Map a single buffer of the indicated size for PCI DMA in streaming
254*4882a593Smuzhiyun mode. The 32-bit PCI bus mastering address to use is returned.
255*4882a593Smuzhiyun Once the device is given the dma address, the device owns this memory
256*4882a593Smuzhiyun until either pci_unmap_single or pci_dma_sync_single is performed. */
257*4882a593Smuzhiyun
258*4882a593Smuzhiyun static dma_addr_t
pci_map_single_1(struct pci_dev * pdev,void * cpu_addr,size_t size,int dac_allowed)259*4882a593Smuzhiyun pci_map_single_1(struct pci_dev *pdev, void *cpu_addr, size_t size,
260*4882a593Smuzhiyun int dac_allowed)
261*4882a593Smuzhiyun {
262*4882a593Smuzhiyun struct pci_controller *hose = pdev ? pdev->sysdata : pci_isa_hose;
263*4882a593Smuzhiyun dma_addr_t max_dma = pdev ? pdev->dma_mask : ISA_DMA_MASK;
264*4882a593Smuzhiyun struct pci_iommu_arena *arena;
265*4882a593Smuzhiyun long npages, dma_ofs, i;
266*4882a593Smuzhiyun unsigned long paddr;
267*4882a593Smuzhiyun dma_addr_t ret;
268*4882a593Smuzhiyun unsigned int align = 0;
269*4882a593Smuzhiyun struct device *dev = pdev ? &pdev->dev : NULL;
270*4882a593Smuzhiyun
271*4882a593Smuzhiyun paddr = __pa(cpu_addr);
272*4882a593Smuzhiyun
273*4882a593Smuzhiyun #if !DEBUG_NODIRECT
274*4882a593Smuzhiyun /* First check to see if we can use the direct map window. */
275*4882a593Smuzhiyun if (paddr + size + __direct_map_base - 1 <= max_dma
276*4882a593Smuzhiyun && paddr + size <= __direct_map_size) {
277*4882a593Smuzhiyun ret = paddr + __direct_map_base;
278*4882a593Smuzhiyun
279*4882a593Smuzhiyun DBGA2("pci_map_single: [%p,%zx] -> direct %llx from %ps\n",
280*4882a593Smuzhiyun cpu_addr, size, ret, __builtin_return_address(0));
281*4882a593Smuzhiyun
282*4882a593Smuzhiyun return ret;
283*4882a593Smuzhiyun }
284*4882a593Smuzhiyun #endif
285*4882a593Smuzhiyun
286*4882a593Smuzhiyun /* Next, use DAC if selected earlier. */
287*4882a593Smuzhiyun if (dac_allowed) {
288*4882a593Smuzhiyun ret = paddr + alpha_mv.pci_dac_offset;
289*4882a593Smuzhiyun
290*4882a593Smuzhiyun DBGA2("pci_map_single: [%p,%zx] -> DAC %llx from %ps\n",
291*4882a593Smuzhiyun cpu_addr, size, ret, __builtin_return_address(0));
292*4882a593Smuzhiyun
293*4882a593Smuzhiyun return ret;
294*4882a593Smuzhiyun }
295*4882a593Smuzhiyun
296*4882a593Smuzhiyun /* If the machine doesn't define a pci_tbi routine, we have to
297*4882a593Smuzhiyun assume it doesn't support sg mapping, and, since we tried to
298*4882a593Smuzhiyun use direct_map above, it now must be considered an error. */
299*4882a593Smuzhiyun if (! alpha_mv.mv_pci_tbi) {
300*4882a593Smuzhiyun printk_once(KERN_WARNING "pci_map_single: no HW sg\n");
301*4882a593Smuzhiyun return DMA_MAPPING_ERROR;
302*4882a593Smuzhiyun }
303*4882a593Smuzhiyun
304*4882a593Smuzhiyun arena = hose->sg_pci;
305*4882a593Smuzhiyun if (!arena || arena->dma_base + arena->size - 1 > max_dma)
306*4882a593Smuzhiyun arena = hose->sg_isa;
307*4882a593Smuzhiyun
308*4882a593Smuzhiyun npages = iommu_num_pages(paddr, size, PAGE_SIZE);
309*4882a593Smuzhiyun
310*4882a593Smuzhiyun /* Force allocation to 64KB boundary for ISA bridges. */
311*4882a593Smuzhiyun if (pdev && pdev == isa_bridge)
312*4882a593Smuzhiyun align = 8;
313*4882a593Smuzhiyun dma_ofs = iommu_arena_alloc(dev, arena, npages, align);
314*4882a593Smuzhiyun if (dma_ofs < 0) {
315*4882a593Smuzhiyun printk(KERN_WARNING "pci_map_single failed: "
316*4882a593Smuzhiyun "could not allocate dma page tables\n");
317*4882a593Smuzhiyun return DMA_MAPPING_ERROR;
318*4882a593Smuzhiyun }
319*4882a593Smuzhiyun
320*4882a593Smuzhiyun paddr &= PAGE_MASK;
321*4882a593Smuzhiyun for (i = 0; i < npages; ++i, paddr += PAGE_SIZE)
322*4882a593Smuzhiyun arena->ptes[i + dma_ofs] = mk_iommu_pte(paddr);
323*4882a593Smuzhiyun
324*4882a593Smuzhiyun ret = arena->dma_base + dma_ofs * PAGE_SIZE;
325*4882a593Smuzhiyun ret += (unsigned long)cpu_addr & ~PAGE_MASK;
326*4882a593Smuzhiyun
327*4882a593Smuzhiyun DBGA2("pci_map_single: [%p,%zx] np %ld -> sg %llx from %ps\n",
328*4882a593Smuzhiyun cpu_addr, size, npages, ret, __builtin_return_address(0));
329*4882a593Smuzhiyun
330*4882a593Smuzhiyun return ret;
331*4882a593Smuzhiyun }
332*4882a593Smuzhiyun
333*4882a593Smuzhiyun /* Helper for generic DMA-mapping functions. */
alpha_gendev_to_pci(struct device * dev)334*4882a593Smuzhiyun static struct pci_dev *alpha_gendev_to_pci(struct device *dev)
335*4882a593Smuzhiyun {
336*4882a593Smuzhiyun if (dev && dev_is_pci(dev))
337*4882a593Smuzhiyun return to_pci_dev(dev);
338*4882a593Smuzhiyun
339*4882a593Smuzhiyun /* Assume that non-PCI devices asking for DMA are either ISA or EISA,
340*4882a593Smuzhiyun BUG() otherwise. */
341*4882a593Smuzhiyun BUG_ON(!isa_bridge);
342*4882a593Smuzhiyun
343*4882a593Smuzhiyun /* Assume non-busmaster ISA DMA when dma_mask is not set (the ISA
344*4882a593Smuzhiyun bridge is bus master then). */
345*4882a593Smuzhiyun if (!dev || !dev->dma_mask || !*dev->dma_mask)
346*4882a593Smuzhiyun return isa_bridge;
347*4882a593Smuzhiyun
348*4882a593Smuzhiyun /* For EISA bus masters, return isa_bridge (it might have smaller
349*4882a593Smuzhiyun dma_mask due to wiring limitations). */
350*4882a593Smuzhiyun if (*dev->dma_mask >= isa_bridge->dma_mask)
351*4882a593Smuzhiyun return isa_bridge;
352*4882a593Smuzhiyun
353*4882a593Smuzhiyun /* This assumes ISA bus master with dma_mask 0xffffff. */
354*4882a593Smuzhiyun return NULL;
355*4882a593Smuzhiyun }
356*4882a593Smuzhiyun
alpha_pci_map_page(struct device * dev,struct page * page,unsigned long offset,size_t size,enum dma_data_direction dir,unsigned long attrs)357*4882a593Smuzhiyun static dma_addr_t alpha_pci_map_page(struct device *dev, struct page *page,
358*4882a593Smuzhiyun unsigned long offset, size_t size,
359*4882a593Smuzhiyun enum dma_data_direction dir,
360*4882a593Smuzhiyun unsigned long attrs)
361*4882a593Smuzhiyun {
362*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
363*4882a593Smuzhiyun int dac_allowed;
364*4882a593Smuzhiyun
365*4882a593Smuzhiyun BUG_ON(dir == PCI_DMA_NONE);
366*4882a593Smuzhiyun
367*4882a593Smuzhiyun dac_allowed = pdev ? pci_dac_dma_supported(pdev, pdev->dma_mask) : 0;
368*4882a593Smuzhiyun return pci_map_single_1(pdev, (char *)page_address(page) + offset,
369*4882a593Smuzhiyun size, dac_allowed);
370*4882a593Smuzhiyun }
371*4882a593Smuzhiyun
372*4882a593Smuzhiyun /* Unmap a single streaming mode DMA translation. The DMA_ADDR and
373*4882a593Smuzhiyun SIZE must match what was provided for in a previous pci_map_single
374*4882a593Smuzhiyun call. All other usages are undefined. After this call, reads by
375*4882a593Smuzhiyun the cpu to the buffer are guaranteed to see whatever the device
376*4882a593Smuzhiyun wrote there. */
377*4882a593Smuzhiyun
alpha_pci_unmap_page(struct device * dev,dma_addr_t dma_addr,size_t size,enum dma_data_direction dir,unsigned long attrs)378*4882a593Smuzhiyun static void alpha_pci_unmap_page(struct device *dev, dma_addr_t dma_addr,
379*4882a593Smuzhiyun size_t size, enum dma_data_direction dir,
380*4882a593Smuzhiyun unsigned long attrs)
381*4882a593Smuzhiyun {
382*4882a593Smuzhiyun unsigned long flags;
383*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
384*4882a593Smuzhiyun struct pci_controller *hose = pdev ? pdev->sysdata : pci_isa_hose;
385*4882a593Smuzhiyun struct pci_iommu_arena *arena;
386*4882a593Smuzhiyun long dma_ofs, npages;
387*4882a593Smuzhiyun
388*4882a593Smuzhiyun BUG_ON(dir == PCI_DMA_NONE);
389*4882a593Smuzhiyun
390*4882a593Smuzhiyun if (dma_addr >= __direct_map_base
391*4882a593Smuzhiyun && dma_addr < __direct_map_base + __direct_map_size) {
392*4882a593Smuzhiyun /* Nothing to do. */
393*4882a593Smuzhiyun
394*4882a593Smuzhiyun DBGA2("pci_unmap_single: direct [%llx,%zx] from %ps\n",
395*4882a593Smuzhiyun dma_addr, size, __builtin_return_address(0));
396*4882a593Smuzhiyun
397*4882a593Smuzhiyun return;
398*4882a593Smuzhiyun }
399*4882a593Smuzhiyun
400*4882a593Smuzhiyun if (dma_addr > 0xffffffff) {
401*4882a593Smuzhiyun DBGA2("pci64_unmap_single: DAC [%llx,%zx] from %ps\n",
402*4882a593Smuzhiyun dma_addr, size, __builtin_return_address(0));
403*4882a593Smuzhiyun return;
404*4882a593Smuzhiyun }
405*4882a593Smuzhiyun
406*4882a593Smuzhiyun arena = hose->sg_pci;
407*4882a593Smuzhiyun if (!arena || dma_addr < arena->dma_base)
408*4882a593Smuzhiyun arena = hose->sg_isa;
409*4882a593Smuzhiyun
410*4882a593Smuzhiyun dma_ofs = (dma_addr - arena->dma_base) >> PAGE_SHIFT;
411*4882a593Smuzhiyun if (dma_ofs * PAGE_SIZE >= arena->size) {
412*4882a593Smuzhiyun printk(KERN_ERR "Bogus pci_unmap_single: dma_addr %llx "
413*4882a593Smuzhiyun " base %llx size %x\n",
414*4882a593Smuzhiyun dma_addr, arena->dma_base, arena->size);
415*4882a593Smuzhiyun return;
416*4882a593Smuzhiyun BUG();
417*4882a593Smuzhiyun }
418*4882a593Smuzhiyun
419*4882a593Smuzhiyun npages = iommu_num_pages(dma_addr, size, PAGE_SIZE);
420*4882a593Smuzhiyun
421*4882a593Smuzhiyun spin_lock_irqsave(&arena->lock, flags);
422*4882a593Smuzhiyun
423*4882a593Smuzhiyun iommu_arena_free(arena, dma_ofs, npages);
424*4882a593Smuzhiyun
425*4882a593Smuzhiyun /* If we're freeing ptes above the `next_entry' pointer (they
426*4882a593Smuzhiyun may have snuck back into the TLB since the last wrap flush),
427*4882a593Smuzhiyun we need to flush the TLB before reallocating the latter. */
428*4882a593Smuzhiyun if (dma_ofs >= arena->next_entry)
429*4882a593Smuzhiyun alpha_mv.mv_pci_tbi(hose, dma_addr, dma_addr + size - 1);
430*4882a593Smuzhiyun
431*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
432*4882a593Smuzhiyun
433*4882a593Smuzhiyun DBGA2("pci_unmap_single: sg [%llx,%zx] np %ld from %ps\n",
434*4882a593Smuzhiyun dma_addr, size, npages, __builtin_return_address(0));
435*4882a593Smuzhiyun }
436*4882a593Smuzhiyun
437*4882a593Smuzhiyun /* Allocate and map kernel buffer using consistent mode DMA for PCI
438*4882a593Smuzhiyun device. Returns non-NULL cpu-view pointer to the buffer if
439*4882a593Smuzhiyun successful and sets *DMA_ADDRP to the pci side dma address as well,
440*4882a593Smuzhiyun else DMA_ADDRP is undefined. */
441*4882a593Smuzhiyun
alpha_pci_alloc_coherent(struct device * dev,size_t size,dma_addr_t * dma_addrp,gfp_t gfp,unsigned long attrs)442*4882a593Smuzhiyun static void *alpha_pci_alloc_coherent(struct device *dev, size_t size,
443*4882a593Smuzhiyun dma_addr_t *dma_addrp, gfp_t gfp,
444*4882a593Smuzhiyun unsigned long attrs)
445*4882a593Smuzhiyun {
446*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
447*4882a593Smuzhiyun void *cpu_addr;
448*4882a593Smuzhiyun long order = get_order(size);
449*4882a593Smuzhiyun
450*4882a593Smuzhiyun gfp &= ~GFP_DMA;
451*4882a593Smuzhiyun
452*4882a593Smuzhiyun try_again:
453*4882a593Smuzhiyun cpu_addr = (void *)__get_free_pages(gfp | __GFP_ZERO, order);
454*4882a593Smuzhiyun if (! cpu_addr) {
455*4882a593Smuzhiyun printk(KERN_INFO "pci_alloc_consistent: "
456*4882a593Smuzhiyun "get_free_pages failed from %ps\n",
457*4882a593Smuzhiyun __builtin_return_address(0));
458*4882a593Smuzhiyun /* ??? Really atomic allocation? Otherwise we could play
459*4882a593Smuzhiyun with vmalloc and sg if we can't find contiguous memory. */
460*4882a593Smuzhiyun return NULL;
461*4882a593Smuzhiyun }
462*4882a593Smuzhiyun memset(cpu_addr, 0, size);
463*4882a593Smuzhiyun
464*4882a593Smuzhiyun *dma_addrp = pci_map_single_1(pdev, cpu_addr, size, 0);
465*4882a593Smuzhiyun if (*dma_addrp == DMA_MAPPING_ERROR) {
466*4882a593Smuzhiyun free_pages((unsigned long)cpu_addr, order);
467*4882a593Smuzhiyun if (alpha_mv.mv_pci_tbi || (gfp & GFP_DMA))
468*4882a593Smuzhiyun return NULL;
469*4882a593Smuzhiyun /* The address doesn't fit required mask and we
470*4882a593Smuzhiyun do not have iommu. Try again with GFP_DMA. */
471*4882a593Smuzhiyun gfp |= GFP_DMA;
472*4882a593Smuzhiyun goto try_again;
473*4882a593Smuzhiyun }
474*4882a593Smuzhiyun
475*4882a593Smuzhiyun DBGA2("pci_alloc_consistent: %zx -> [%p,%llx] from %ps\n",
476*4882a593Smuzhiyun size, cpu_addr, *dma_addrp, __builtin_return_address(0));
477*4882a593Smuzhiyun
478*4882a593Smuzhiyun return cpu_addr;
479*4882a593Smuzhiyun }
480*4882a593Smuzhiyun
481*4882a593Smuzhiyun /* Free and unmap a consistent DMA buffer. CPU_ADDR and DMA_ADDR must
482*4882a593Smuzhiyun be values that were returned from pci_alloc_consistent. SIZE must
483*4882a593Smuzhiyun be the same as what as passed into pci_alloc_consistent.
484*4882a593Smuzhiyun References to the memory and mappings associated with CPU_ADDR or
485*4882a593Smuzhiyun DMA_ADDR past this call are illegal. */
486*4882a593Smuzhiyun
alpha_pci_free_coherent(struct device * dev,size_t size,void * cpu_addr,dma_addr_t dma_addr,unsigned long attrs)487*4882a593Smuzhiyun static void alpha_pci_free_coherent(struct device *dev, size_t size,
488*4882a593Smuzhiyun void *cpu_addr, dma_addr_t dma_addr,
489*4882a593Smuzhiyun unsigned long attrs)
490*4882a593Smuzhiyun {
491*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
492*4882a593Smuzhiyun pci_unmap_single(pdev, dma_addr, size, PCI_DMA_BIDIRECTIONAL);
493*4882a593Smuzhiyun free_pages((unsigned long)cpu_addr, get_order(size));
494*4882a593Smuzhiyun
495*4882a593Smuzhiyun DBGA2("pci_free_consistent: [%llx,%zx] from %ps\n",
496*4882a593Smuzhiyun dma_addr, size, __builtin_return_address(0));
497*4882a593Smuzhiyun }
498*4882a593Smuzhiyun
499*4882a593Smuzhiyun /* Classify the elements of the scatterlist. Write dma_address
500*4882a593Smuzhiyun of each element with:
501*4882a593Smuzhiyun 0 : Followers all physically adjacent.
502*4882a593Smuzhiyun 1 : Followers all virtually adjacent.
503*4882a593Smuzhiyun -1 : Not leader, physically adjacent to previous.
504*4882a593Smuzhiyun -2 : Not leader, virtually adjacent to previous.
505*4882a593Smuzhiyun Write dma_length of each leader with the combined lengths of
506*4882a593Smuzhiyun the mergable followers. */
507*4882a593Smuzhiyun
508*4882a593Smuzhiyun #define SG_ENT_VIRT_ADDRESS(SG) (sg_virt((SG)))
509*4882a593Smuzhiyun #define SG_ENT_PHYS_ADDRESS(SG) __pa(SG_ENT_VIRT_ADDRESS(SG))
510*4882a593Smuzhiyun
511*4882a593Smuzhiyun static void
sg_classify(struct device * dev,struct scatterlist * sg,struct scatterlist * end,int virt_ok)512*4882a593Smuzhiyun sg_classify(struct device *dev, struct scatterlist *sg, struct scatterlist *end,
513*4882a593Smuzhiyun int virt_ok)
514*4882a593Smuzhiyun {
515*4882a593Smuzhiyun unsigned long next_paddr;
516*4882a593Smuzhiyun struct scatterlist *leader;
517*4882a593Smuzhiyun long leader_flag, leader_length;
518*4882a593Smuzhiyun unsigned int max_seg_size;
519*4882a593Smuzhiyun
520*4882a593Smuzhiyun leader = sg;
521*4882a593Smuzhiyun leader_flag = 0;
522*4882a593Smuzhiyun leader_length = leader->length;
523*4882a593Smuzhiyun next_paddr = SG_ENT_PHYS_ADDRESS(leader) + leader_length;
524*4882a593Smuzhiyun
525*4882a593Smuzhiyun /* we will not marge sg without device. */
526*4882a593Smuzhiyun max_seg_size = dev ? dma_get_max_seg_size(dev) : 0;
527*4882a593Smuzhiyun for (++sg; sg < end; ++sg) {
528*4882a593Smuzhiyun unsigned long addr, len;
529*4882a593Smuzhiyun addr = SG_ENT_PHYS_ADDRESS(sg);
530*4882a593Smuzhiyun len = sg->length;
531*4882a593Smuzhiyun
532*4882a593Smuzhiyun if (leader_length + len > max_seg_size)
533*4882a593Smuzhiyun goto new_segment;
534*4882a593Smuzhiyun
535*4882a593Smuzhiyun if (next_paddr == addr) {
536*4882a593Smuzhiyun sg->dma_address = -1;
537*4882a593Smuzhiyun leader_length += len;
538*4882a593Smuzhiyun } else if (((next_paddr | addr) & ~PAGE_MASK) == 0 && virt_ok) {
539*4882a593Smuzhiyun sg->dma_address = -2;
540*4882a593Smuzhiyun leader_flag = 1;
541*4882a593Smuzhiyun leader_length += len;
542*4882a593Smuzhiyun } else {
543*4882a593Smuzhiyun new_segment:
544*4882a593Smuzhiyun leader->dma_address = leader_flag;
545*4882a593Smuzhiyun leader->dma_length = leader_length;
546*4882a593Smuzhiyun leader = sg;
547*4882a593Smuzhiyun leader_flag = 0;
548*4882a593Smuzhiyun leader_length = len;
549*4882a593Smuzhiyun }
550*4882a593Smuzhiyun
551*4882a593Smuzhiyun next_paddr = addr + len;
552*4882a593Smuzhiyun }
553*4882a593Smuzhiyun
554*4882a593Smuzhiyun leader->dma_address = leader_flag;
555*4882a593Smuzhiyun leader->dma_length = leader_length;
556*4882a593Smuzhiyun }
557*4882a593Smuzhiyun
558*4882a593Smuzhiyun /* Given a scatterlist leader, choose an allocation method and fill
559*4882a593Smuzhiyun in the blanks. */
560*4882a593Smuzhiyun
561*4882a593Smuzhiyun static int
sg_fill(struct device * dev,struct scatterlist * leader,struct scatterlist * end,struct scatterlist * out,struct pci_iommu_arena * arena,dma_addr_t max_dma,int dac_allowed)562*4882a593Smuzhiyun sg_fill(struct device *dev, struct scatterlist *leader, struct scatterlist *end,
563*4882a593Smuzhiyun struct scatterlist *out, struct pci_iommu_arena *arena,
564*4882a593Smuzhiyun dma_addr_t max_dma, int dac_allowed)
565*4882a593Smuzhiyun {
566*4882a593Smuzhiyun unsigned long paddr = SG_ENT_PHYS_ADDRESS(leader);
567*4882a593Smuzhiyun long size = leader->dma_length;
568*4882a593Smuzhiyun struct scatterlist *sg;
569*4882a593Smuzhiyun unsigned long *ptes;
570*4882a593Smuzhiyun long npages, dma_ofs, i;
571*4882a593Smuzhiyun
572*4882a593Smuzhiyun #if !DEBUG_NODIRECT
573*4882a593Smuzhiyun /* If everything is physically contiguous, and the addresses
574*4882a593Smuzhiyun fall into the direct-map window, use it. */
575*4882a593Smuzhiyun if (leader->dma_address == 0
576*4882a593Smuzhiyun && paddr + size + __direct_map_base - 1 <= max_dma
577*4882a593Smuzhiyun && paddr + size <= __direct_map_size) {
578*4882a593Smuzhiyun out->dma_address = paddr + __direct_map_base;
579*4882a593Smuzhiyun out->dma_length = size;
580*4882a593Smuzhiyun
581*4882a593Smuzhiyun DBGA(" sg_fill: [%p,%lx] -> direct %llx\n",
582*4882a593Smuzhiyun __va(paddr), size, out->dma_address);
583*4882a593Smuzhiyun
584*4882a593Smuzhiyun return 0;
585*4882a593Smuzhiyun }
586*4882a593Smuzhiyun #endif
587*4882a593Smuzhiyun
588*4882a593Smuzhiyun /* If physically contiguous and DAC is available, use it. */
589*4882a593Smuzhiyun if (leader->dma_address == 0 && dac_allowed) {
590*4882a593Smuzhiyun out->dma_address = paddr + alpha_mv.pci_dac_offset;
591*4882a593Smuzhiyun out->dma_length = size;
592*4882a593Smuzhiyun
593*4882a593Smuzhiyun DBGA(" sg_fill: [%p,%lx] -> DAC %llx\n",
594*4882a593Smuzhiyun __va(paddr), size, out->dma_address);
595*4882a593Smuzhiyun
596*4882a593Smuzhiyun return 0;
597*4882a593Smuzhiyun }
598*4882a593Smuzhiyun
599*4882a593Smuzhiyun /* Otherwise, we'll use the iommu to make the pages virtually
600*4882a593Smuzhiyun contiguous. */
601*4882a593Smuzhiyun
602*4882a593Smuzhiyun paddr &= ~PAGE_MASK;
603*4882a593Smuzhiyun npages = iommu_num_pages(paddr, size, PAGE_SIZE);
604*4882a593Smuzhiyun dma_ofs = iommu_arena_alloc(dev, arena, npages, 0);
605*4882a593Smuzhiyun if (dma_ofs < 0) {
606*4882a593Smuzhiyun /* If we attempted a direct map above but failed, die. */
607*4882a593Smuzhiyun if (leader->dma_address == 0)
608*4882a593Smuzhiyun return -1;
609*4882a593Smuzhiyun
610*4882a593Smuzhiyun /* Otherwise, break up the remaining virtually contiguous
611*4882a593Smuzhiyun hunks into individual direct maps and retry. */
612*4882a593Smuzhiyun sg_classify(dev, leader, end, 0);
613*4882a593Smuzhiyun return sg_fill(dev, leader, end, out, arena, max_dma, dac_allowed);
614*4882a593Smuzhiyun }
615*4882a593Smuzhiyun
616*4882a593Smuzhiyun out->dma_address = arena->dma_base + dma_ofs*PAGE_SIZE + paddr;
617*4882a593Smuzhiyun out->dma_length = size;
618*4882a593Smuzhiyun
619*4882a593Smuzhiyun DBGA(" sg_fill: [%p,%lx] -> sg %llx np %ld\n",
620*4882a593Smuzhiyun __va(paddr), size, out->dma_address, npages);
621*4882a593Smuzhiyun
622*4882a593Smuzhiyun /* All virtually contiguous. We need to find the length of each
623*4882a593Smuzhiyun physically contiguous subsegment to fill in the ptes. */
624*4882a593Smuzhiyun ptes = &arena->ptes[dma_ofs];
625*4882a593Smuzhiyun sg = leader;
626*4882a593Smuzhiyun do {
627*4882a593Smuzhiyun #if DEBUG_ALLOC > 0
628*4882a593Smuzhiyun struct scatterlist *last_sg = sg;
629*4882a593Smuzhiyun #endif
630*4882a593Smuzhiyun
631*4882a593Smuzhiyun size = sg->length;
632*4882a593Smuzhiyun paddr = SG_ENT_PHYS_ADDRESS(sg);
633*4882a593Smuzhiyun
634*4882a593Smuzhiyun while (sg+1 < end && (int) sg[1].dma_address == -1) {
635*4882a593Smuzhiyun size += sg[1].length;
636*4882a593Smuzhiyun sg = sg_next(sg);
637*4882a593Smuzhiyun }
638*4882a593Smuzhiyun
639*4882a593Smuzhiyun npages = iommu_num_pages(paddr, size, PAGE_SIZE);
640*4882a593Smuzhiyun
641*4882a593Smuzhiyun paddr &= PAGE_MASK;
642*4882a593Smuzhiyun for (i = 0; i < npages; ++i, paddr += PAGE_SIZE)
643*4882a593Smuzhiyun *ptes++ = mk_iommu_pte(paddr);
644*4882a593Smuzhiyun
645*4882a593Smuzhiyun #if DEBUG_ALLOC > 0
646*4882a593Smuzhiyun DBGA(" (%ld) [%p,%x] np %ld\n",
647*4882a593Smuzhiyun last_sg - leader, SG_ENT_VIRT_ADDRESS(last_sg),
648*4882a593Smuzhiyun last_sg->length, npages);
649*4882a593Smuzhiyun while (++last_sg <= sg) {
650*4882a593Smuzhiyun DBGA(" (%ld) [%p,%x] cont\n",
651*4882a593Smuzhiyun last_sg - leader, SG_ENT_VIRT_ADDRESS(last_sg),
652*4882a593Smuzhiyun last_sg->length);
653*4882a593Smuzhiyun }
654*4882a593Smuzhiyun #endif
655*4882a593Smuzhiyun } while (++sg < end && (int) sg->dma_address < 0);
656*4882a593Smuzhiyun
657*4882a593Smuzhiyun return 1;
658*4882a593Smuzhiyun }
659*4882a593Smuzhiyun
alpha_pci_map_sg(struct device * dev,struct scatterlist * sg,int nents,enum dma_data_direction dir,unsigned long attrs)660*4882a593Smuzhiyun static int alpha_pci_map_sg(struct device *dev, struct scatterlist *sg,
661*4882a593Smuzhiyun int nents, enum dma_data_direction dir,
662*4882a593Smuzhiyun unsigned long attrs)
663*4882a593Smuzhiyun {
664*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
665*4882a593Smuzhiyun struct scatterlist *start, *end, *out;
666*4882a593Smuzhiyun struct pci_controller *hose;
667*4882a593Smuzhiyun struct pci_iommu_arena *arena;
668*4882a593Smuzhiyun dma_addr_t max_dma;
669*4882a593Smuzhiyun int dac_allowed;
670*4882a593Smuzhiyun
671*4882a593Smuzhiyun BUG_ON(dir == PCI_DMA_NONE);
672*4882a593Smuzhiyun
673*4882a593Smuzhiyun dac_allowed = dev ? pci_dac_dma_supported(pdev, pdev->dma_mask) : 0;
674*4882a593Smuzhiyun
675*4882a593Smuzhiyun /* Fast path single entry scatterlists. */
676*4882a593Smuzhiyun if (nents == 1) {
677*4882a593Smuzhiyun sg->dma_length = sg->length;
678*4882a593Smuzhiyun sg->dma_address
679*4882a593Smuzhiyun = pci_map_single_1(pdev, SG_ENT_VIRT_ADDRESS(sg),
680*4882a593Smuzhiyun sg->length, dac_allowed);
681*4882a593Smuzhiyun return sg->dma_address != DMA_MAPPING_ERROR;
682*4882a593Smuzhiyun }
683*4882a593Smuzhiyun
684*4882a593Smuzhiyun start = sg;
685*4882a593Smuzhiyun end = sg + nents;
686*4882a593Smuzhiyun
687*4882a593Smuzhiyun /* First, prepare information about the entries. */
688*4882a593Smuzhiyun sg_classify(dev, sg, end, alpha_mv.mv_pci_tbi != 0);
689*4882a593Smuzhiyun
690*4882a593Smuzhiyun /* Second, figure out where we're going to map things. */
691*4882a593Smuzhiyun if (alpha_mv.mv_pci_tbi) {
692*4882a593Smuzhiyun hose = pdev ? pdev->sysdata : pci_isa_hose;
693*4882a593Smuzhiyun max_dma = pdev ? pdev->dma_mask : ISA_DMA_MASK;
694*4882a593Smuzhiyun arena = hose->sg_pci;
695*4882a593Smuzhiyun if (!arena || arena->dma_base + arena->size - 1 > max_dma)
696*4882a593Smuzhiyun arena = hose->sg_isa;
697*4882a593Smuzhiyun } else {
698*4882a593Smuzhiyun max_dma = -1;
699*4882a593Smuzhiyun arena = NULL;
700*4882a593Smuzhiyun hose = NULL;
701*4882a593Smuzhiyun }
702*4882a593Smuzhiyun
703*4882a593Smuzhiyun /* Third, iterate over the scatterlist leaders and allocate
704*4882a593Smuzhiyun dma space as needed. */
705*4882a593Smuzhiyun for (out = sg; sg < end; ++sg) {
706*4882a593Smuzhiyun if ((int) sg->dma_address < 0)
707*4882a593Smuzhiyun continue;
708*4882a593Smuzhiyun if (sg_fill(dev, sg, end, out, arena, max_dma, dac_allowed) < 0)
709*4882a593Smuzhiyun goto error;
710*4882a593Smuzhiyun out++;
711*4882a593Smuzhiyun }
712*4882a593Smuzhiyun
713*4882a593Smuzhiyun /* Mark the end of the list for pci_unmap_sg. */
714*4882a593Smuzhiyun if (out < end)
715*4882a593Smuzhiyun out->dma_length = 0;
716*4882a593Smuzhiyun
717*4882a593Smuzhiyun if (out - start == 0)
718*4882a593Smuzhiyun printk(KERN_WARNING "pci_map_sg failed: no entries?\n");
719*4882a593Smuzhiyun DBGA("pci_map_sg: %ld entries\n", out - start);
720*4882a593Smuzhiyun
721*4882a593Smuzhiyun return out - start;
722*4882a593Smuzhiyun
723*4882a593Smuzhiyun error:
724*4882a593Smuzhiyun printk(KERN_WARNING "pci_map_sg failed: "
725*4882a593Smuzhiyun "could not allocate dma page tables\n");
726*4882a593Smuzhiyun
727*4882a593Smuzhiyun /* Some allocation failed while mapping the scatterlist
728*4882a593Smuzhiyun entries. Unmap them now. */
729*4882a593Smuzhiyun if (out > start)
730*4882a593Smuzhiyun pci_unmap_sg(pdev, start, out - start, dir);
731*4882a593Smuzhiyun return 0;
732*4882a593Smuzhiyun }
733*4882a593Smuzhiyun
734*4882a593Smuzhiyun /* Unmap a set of streaming mode DMA translations. Again, cpu read
735*4882a593Smuzhiyun rules concerning calls here are the same as for pci_unmap_single()
736*4882a593Smuzhiyun above. */
737*4882a593Smuzhiyun
alpha_pci_unmap_sg(struct device * dev,struct scatterlist * sg,int nents,enum dma_data_direction dir,unsigned long attrs)738*4882a593Smuzhiyun static void alpha_pci_unmap_sg(struct device *dev, struct scatterlist *sg,
739*4882a593Smuzhiyun int nents, enum dma_data_direction dir,
740*4882a593Smuzhiyun unsigned long attrs)
741*4882a593Smuzhiyun {
742*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
743*4882a593Smuzhiyun unsigned long flags;
744*4882a593Smuzhiyun struct pci_controller *hose;
745*4882a593Smuzhiyun struct pci_iommu_arena *arena;
746*4882a593Smuzhiyun struct scatterlist *end;
747*4882a593Smuzhiyun dma_addr_t max_dma;
748*4882a593Smuzhiyun dma_addr_t fbeg, fend;
749*4882a593Smuzhiyun
750*4882a593Smuzhiyun BUG_ON(dir == PCI_DMA_NONE);
751*4882a593Smuzhiyun
752*4882a593Smuzhiyun if (! alpha_mv.mv_pci_tbi)
753*4882a593Smuzhiyun return;
754*4882a593Smuzhiyun
755*4882a593Smuzhiyun hose = pdev ? pdev->sysdata : pci_isa_hose;
756*4882a593Smuzhiyun max_dma = pdev ? pdev->dma_mask : ISA_DMA_MASK;
757*4882a593Smuzhiyun arena = hose->sg_pci;
758*4882a593Smuzhiyun if (!arena || arena->dma_base + arena->size - 1 > max_dma)
759*4882a593Smuzhiyun arena = hose->sg_isa;
760*4882a593Smuzhiyun
761*4882a593Smuzhiyun fbeg = -1, fend = 0;
762*4882a593Smuzhiyun
763*4882a593Smuzhiyun spin_lock_irqsave(&arena->lock, flags);
764*4882a593Smuzhiyun
765*4882a593Smuzhiyun for (end = sg + nents; sg < end; ++sg) {
766*4882a593Smuzhiyun dma_addr_t addr;
767*4882a593Smuzhiyun size_t size;
768*4882a593Smuzhiyun long npages, ofs;
769*4882a593Smuzhiyun dma_addr_t tend;
770*4882a593Smuzhiyun
771*4882a593Smuzhiyun addr = sg->dma_address;
772*4882a593Smuzhiyun size = sg->dma_length;
773*4882a593Smuzhiyun if (!size)
774*4882a593Smuzhiyun break;
775*4882a593Smuzhiyun
776*4882a593Smuzhiyun if (addr > 0xffffffff) {
777*4882a593Smuzhiyun /* It's a DAC address -- nothing to do. */
778*4882a593Smuzhiyun DBGA(" (%ld) DAC [%llx,%zx]\n",
779*4882a593Smuzhiyun sg - end + nents, addr, size);
780*4882a593Smuzhiyun continue;
781*4882a593Smuzhiyun }
782*4882a593Smuzhiyun
783*4882a593Smuzhiyun if (addr >= __direct_map_base
784*4882a593Smuzhiyun && addr < __direct_map_base + __direct_map_size) {
785*4882a593Smuzhiyun /* Nothing to do. */
786*4882a593Smuzhiyun DBGA(" (%ld) direct [%llx,%zx]\n",
787*4882a593Smuzhiyun sg - end + nents, addr, size);
788*4882a593Smuzhiyun continue;
789*4882a593Smuzhiyun }
790*4882a593Smuzhiyun
791*4882a593Smuzhiyun DBGA(" (%ld) sg [%llx,%zx]\n",
792*4882a593Smuzhiyun sg - end + nents, addr, size);
793*4882a593Smuzhiyun
794*4882a593Smuzhiyun npages = iommu_num_pages(addr, size, PAGE_SIZE);
795*4882a593Smuzhiyun ofs = (addr - arena->dma_base) >> PAGE_SHIFT;
796*4882a593Smuzhiyun iommu_arena_free(arena, ofs, npages);
797*4882a593Smuzhiyun
798*4882a593Smuzhiyun tend = addr + size - 1;
799*4882a593Smuzhiyun if (fbeg > addr) fbeg = addr;
800*4882a593Smuzhiyun if (fend < tend) fend = tend;
801*4882a593Smuzhiyun }
802*4882a593Smuzhiyun
803*4882a593Smuzhiyun /* If we're freeing ptes above the `next_entry' pointer (they
804*4882a593Smuzhiyun may have snuck back into the TLB since the last wrap flush),
805*4882a593Smuzhiyun we need to flush the TLB before reallocating the latter. */
806*4882a593Smuzhiyun if ((fend - arena->dma_base) >> PAGE_SHIFT >= arena->next_entry)
807*4882a593Smuzhiyun alpha_mv.mv_pci_tbi(hose, fbeg, fend);
808*4882a593Smuzhiyun
809*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
810*4882a593Smuzhiyun
811*4882a593Smuzhiyun DBGA("pci_unmap_sg: %ld entries\n", nents - (end - sg));
812*4882a593Smuzhiyun }
813*4882a593Smuzhiyun
814*4882a593Smuzhiyun /* Return whether the given PCI device DMA address mask can be
815*4882a593Smuzhiyun supported properly. */
816*4882a593Smuzhiyun
alpha_pci_supported(struct device * dev,u64 mask)817*4882a593Smuzhiyun static int alpha_pci_supported(struct device *dev, u64 mask)
818*4882a593Smuzhiyun {
819*4882a593Smuzhiyun struct pci_dev *pdev = alpha_gendev_to_pci(dev);
820*4882a593Smuzhiyun struct pci_controller *hose;
821*4882a593Smuzhiyun struct pci_iommu_arena *arena;
822*4882a593Smuzhiyun
823*4882a593Smuzhiyun /* If there exists a direct map, and the mask fits either
824*4882a593Smuzhiyun the entire direct mapped space or the total system memory as
825*4882a593Smuzhiyun shifted by the map base */
826*4882a593Smuzhiyun if (__direct_map_size != 0
827*4882a593Smuzhiyun && (__direct_map_base + __direct_map_size - 1 <= mask ||
828*4882a593Smuzhiyun __direct_map_base + (max_low_pfn << PAGE_SHIFT) - 1 <= mask))
829*4882a593Smuzhiyun return 1;
830*4882a593Smuzhiyun
831*4882a593Smuzhiyun /* Check that we have a scatter-gather arena that fits. */
832*4882a593Smuzhiyun hose = pdev ? pdev->sysdata : pci_isa_hose;
833*4882a593Smuzhiyun arena = hose->sg_isa;
834*4882a593Smuzhiyun if (arena && arena->dma_base + arena->size - 1 <= mask)
835*4882a593Smuzhiyun return 1;
836*4882a593Smuzhiyun arena = hose->sg_pci;
837*4882a593Smuzhiyun if (arena && arena->dma_base + arena->size - 1 <= mask)
838*4882a593Smuzhiyun return 1;
839*4882a593Smuzhiyun
840*4882a593Smuzhiyun /* As last resort try ZONE_DMA. */
841*4882a593Smuzhiyun if (!__direct_map_base && MAX_DMA_ADDRESS - IDENT_ADDR - 1 <= mask)
842*4882a593Smuzhiyun return 1;
843*4882a593Smuzhiyun
844*4882a593Smuzhiyun return 0;
845*4882a593Smuzhiyun }
846*4882a593Smuzhiyun
847*4882a593Smuzhiyun
848*4882a593Smuzhiyun /*
849*4882a593Smuzhiyun * AGP GART extensions to the IOMMU
850*4882a593Smuzhiyun */
851*4882a593Smuzhiyun int
iommu_reserve(struct pci_iommu_arena * arena,long pg_count,long align_mask)852*4882a593Smuzhiyun iommu_reserve(struct pci_iommu_arena *arena, long pg_count, long align_mask)
853*4882a593Smuzhiyun {
854*4882a593Smuzhiyun unsigned long flags;
855*4882a593Smuzhiyun unsigned long *ptes;
856*4882a593Smuzhiyun long i, p;
857*4882a593Smuzhiyun
858*4882a593Smuzhiyun if (!arena) return -EINVAL;
859*4882a593Smuzhiyun
860*4882a593Smuzhiyun spin_lock_irqsave(&arena->lock, flags);
861*4882a593Smuzhiyun
862*4882a593Smuzhiyun /* Search for N empty ptes. */
863*4882a593Smuzhiyun ptes = arena->ptes;
864*4882a593Smuzhiyun p = iommu_arena_find_pages(NULL, arena, pg_count, align_mask);
865*4882a593Smuzhiyun if (p < 0) {
866*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
867*4882a593Smuzhiyun return -1;
868*4882a593Smuzhiyun }
869*4882a593Smuzhiyun
870*4882a593Smuzhiyun /* Success. Mark them all reserved (ie not zero and invalid)
871*4882a593Smuzhiyun for the iommu tlb that could load them from under us.
872*4882a593Smuzhiyun They will be filled in with valid bits by _bind() */
873*4882a593Smuzhiyun for (i = 0; i < pg_count; ++i)
874*4882a593Smuzhiyun ptes[p+i] = IOMMU_RESERVED_PTE;
875*4882a593Smuzhiyun
876*4882a593Smuzhiyun arena->next_entry = p + pg_count;
877*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
878*4882a593Smuzhiyun
879*4882a593Smuzhiyun return p;
880*4882a593Smuzhiyun }
881*4882a593Smuzhiyun
882*4882a593Smuzhiyun int
iommu_release(struct pci_iommu_arena * arena,long pg_start,long pg_count)883*4882a593Smuzhiyun iommu_release(struct pci_iommu_arena *arena, long pg_start, long pg_count)
884*4882a593Smuzhiyun {
885*4882a593Smuzhiyun unsigned long *ptes;
886*4882a593Smuzhiyun long i;
887*4882a593Smuzhiyun
888*4882a593Smuzhiyun if (!arena) return -EINVAL;
889*4882a593Smuzhiyun
890*4882a593Smuzhiyun ptes = arena->ptes;
891*4882a593Smuzhiyun
892*4882a593Smuzhiyun /* Make sure they're all reserved first... */
893*4882a593Smuzhiyun for(i = pg_start; i < pg_start + pg_count; i++)
894*4882a593Smuzhiyun if (ptes[i] != IOMMU_RESERVED_PTE)
895*4882a593Smuzhiyun return -EBUSY;
896*4882a593Smuzhiyun
897*4882a593Smuzhiyun iommu_arena_free(arena, pg_start, pg_count);
898*4882a593Smuzhiyun return 0;
899*4882a593Smuzhiyun }
900*4882a593Smuzhiyun
901*4882a593Smuzhiyun int
iommu_bind(struct pci_iommu_arena * arena,long pg_start,long pg_count,struct page ** pages)902*4882a593Smuzhiyun iommu_bind(struct pci_iommu_arena *arena, long pg_start, long pg_count,
903*4882a593Smuzhiyun struct page **pages)
904*4882a593Smuzhiyun {
905*4882a593Smuzhiyun unsigned long flags;
906*4882a593Smuzhiyun unsigned long *ptes;
907*4882a593Smuzhiyun long i, j;
908*4882a593Smuzhiyun
909*4882a593Smuzhiyun if (!arena) return -EINVAL;
910*4882a593Smuzhiyun
911*4882a593Smuzhiyun spin_lock_irqsave(&arena->lock, flags);
912*4882a593Smuzhiyun
913*4882a593Smuzhiyun ptes = arena->ptes;
914*4882a593Smuzhiyun
915*4882a593Smuzhiyun for(j = pg_start; j < pg_start + pg_count; j++) {
916*4882a593Smuzhiyun if (ptes[j] != IOMMU_RESERVED_PTE) {
917*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
918*4882a593Smuzhiyun return -EBUSY;
919*4882a593Smuzhiyun }
920*4882a593Smuzhiyun }
921*4882a593Smuzhiyun
922*4882a593Smuzhiyun for(i = 0, j = pg_start; i < pg_count; i++, j++)
923*4882a593Smuzhiyun ptes[j] = mk_iommu_pte(page_to_phys(pages[i]));
924*4882a593Smuzhiyun
925*4882a593Smuzhiyun spin_unlock_irqrestore(&arena->lock, flags);
926*4882a593Smuzhiyun
927*4882a593Smuzhiyun return 0;
928*4882a593Smuzhiyun }
929*4882a593Smuzhiyun
930*4882a593Smuzhiyun int
iommu_unbind(struct pci_iommu_arena * arena,long pg_start,long pg_count)931*4882a593Smuzhiyun iommu_unbind(struct pci_iommu_arena *arena, long pg_start, long pg_count)
932*4882a593Smuzhiyun {
933*4882a593Smuzhiyun unsigned long *p;
934*4882a593Smuzhiyun long i;
935*4882a593Smuzhiyun
936*4882a593Smuzhiyun if (!arena) return -EINVAL;
937*4882a593Smuzhiyun
938*4882a593Smuzhiyun p = arena->ptes + pg_start;
939*4882a593Smuzhiyun for(i = 0; i < pg_count; i++)
940*4882a593Smuzhiyun p[i] = IOMMU_RESERVED_PTE;
941*4882a593Smuzhiyun
942*4882a593Smuzhiyun return 0;
943*4882a593Smuzhiyun }
944*4882a593Smuzhiyun
945*4882a593Smuzhiyun const struct dma_map_ops alpha_pci_ops = {
946*4882a593Smuzhiyun .alloc = alpha_pci_alloc_coherent,
947*4882a593Smuzhiyun .free = alpha_pci_free_coherent,
948*4882a593Smuzhiyun .map_page = alpha_pci_map_page,
949*4882a593Smuzhiyun .unmap_page = alpha_pci_unmap_page,
950*4882a593Smuzhiyun .map_sg = alpha_pci_map_sg,
951*4882a593Smuzhiyun .unmap_sg = alpha_pci_unmap_sg,
952*4882a593Smuzhiyun .dma_supported = alpha_pci_supported,
953*4882a593Smuzhiyun .mmap = dma_common_mmap,
954*4882a593Smuzhiyun .get_sgtable = dma_common_get_sgtable,
955*4882a593Smuzhiyun .alloc_pages = dma_common_alloc_pages,
956*4882a593Smuzhiyun .free_pages = dma_common_free_pages,
957*4882a593Smuzhiyun };
958*4882a593Smuzhiyun EXPORT_SYMBOL(alpha_pci_ops);
959