1/* 2 * Copyright (C) 2001 David J. Mckay (david.mckay@st.com) 3 * Copyright (C) 2003 Paul Mundt (lethal@linux-sh.org) 4 * 5 * May be copied or modified under the terms of the GNU General Public 6 * License. See linux/COPYING for more information. 7 * 8 * Dynamic DMA mapping support. 9 */ 10#include <linux/types.h> 11#include <linux/mm.h> 12#include <linux/string.h> 13#include <linux/pci.h> 14#include <asm/io.h> 15 16void *consistent_alloc(struct pci_dev *hwdev, size_t size, 17 dma_addr_t *dma_handle) 18{ 19 void *ret; 20 int gfp = GFP_ATOMIC; 21 void *vp; 22 23 if (hwdev == NULL || hwdev->dma_mask != 0xffffffff) 24 gfp |= GFP_DMA; 25 26 ret = (void *)__get_free_pages(gfp, get_order(size)); 27 28 /* now call our friend ioremap_nocache to give us an uncached area */ 29 vp = ioremap_nocache(virt_to_phys(ret), size); 30 31 if (vp != NULL) { 32 memset(vp, 0, size); 33 *dma_handle = virt_to_bus(ret); 34 dma_cache_wback_inv((unsigned long)ret, size); 35 } 36 37 return vp; 38} 39 40void consistent_free(struct pci_dev *hwdev, size_t size, 41 void *vaddr, dma_addr_t dma_handle) 42{ 43 void *alloc; 44 45 alloc = bus_to_virt((unsigned long)dma_handle); 46 free_pages((unsigned long)alloc, get_order(size)); 47 48 iounmap(vaddr); 49} 50