include cleanup: Update gfp.h and slab.h includes to prepare for breaking implicit...
[GitHub/mt8127/android_kernel_alcatel_ttab.git] / arch / xtensa / kernel / pci-dma.c
index 1ff82268e8eacf354e5f16eae1a9ea182d3ca191..2783fda76ddc18f052494c7b9010db3e0e208cfa 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * arch/xtensa/pci-dma.c
+ * arch/xtensa/kernel/pci-dma.c
  *
  * DMA coherent memory allocation.
  *
@@ -20,6 +20,7 @@
 #include <linux/mm.h>
 #include <linux/string.h>
 #include <linux/pci.h>
+#include <linux/gfp.h>
 #include <asm/io.h>
 #include <asm/cacheflush.h>
 
  */
 
 void *
-dma_alloc_coherent(struct device *dev, size_t size, dma_addr_t *handle, gfp_t gfp)
+dma_alloc_coherent(struct device *dev,size_t size,dma_addr_t *handle,gfp_t flag)
 {
-       void *ret;
+       unsigned long ret;
+       unsigned long uncached = 0;
 
        /* ignore region speicifiers */
-       gfp &= ~(__GFP_DMA | __GFP_HIGHMEM);
 
-       if (dev == NULL || (*dev->dma_mask < 0xffffffff))
-               gfp |= GFP_DMA;
-       ret = (void *)__get_free_pages(gfp, get_order(size));
+       flag &= ~(__GFP_DMA | __GFP_HIGHMEM);
 
-       if (ret != NULL) {
-               memset(ret, 0, size);
-               *handle = virt_to_bus(ret);
+       if (dev == NULL || (dev->coherent_dma_mask < 0xffffffff))
+               flag |= GFP_DMA;
+       ret = (unsigned long)__get_free_pages(flag, get_order(size));
+
+       if (ret == 0)
+               return NULL;
+
+       /* We currently don't support coherent memory outside KSEG */
+
+       if (ret < XCHAL_KSEG_CACHED_VADDR
+           || ret >= XCHAL_KSEG_CACHED_VADDR + XCHAL_KSEG_SIZE)
+               BUG();
+
+
+       if (ret != 0) {
+               memset((void*) ret, 0, size);
+               uncached = ret+XCHAL_KSEG_BYPASS_VADDR-XCHAL_KSEG_CACHED_VADDR;
+               *handle = virt_to_bus((void*)ret);
+               __flush_invalidate_dcache_range(ret, size);
        }
-       return (void*) BYPASS_ADDR((unsigned long)ret);
+
+       return (void*)uncached;
 }
 
 void dma_free_coherent(struct device *hwdev, size_t size,
                         void *vaddr, dma_addr_t dma_handle)
 {
-       free_pages(CACHED_ADDR((unsigned long)vaddr), get_order(size));
+       long addr=(long)vaddr+XCHAL_KSEG_CACHED_VADDR-XCHAL_KSEG_BYPASS_VADDR;
+
+       if (addr < 0 || addr >= XCHAL_KSEG_SIZE)
+               BUG();
+
+       free_pages(addr, get_order(size));
 }