On Sat, Mar 19, 2005 at 04:17:51PM -0600, Matt Domsch wrote:
> OK, then how's this for review?  Compiles clean, can't test it myself
> for a few days.
> 
> -             int high = 0, mmu;
> -             if (((unsigned long)virt_to_bus(memory) + size) > 0xffffffffUL)
> -                     high = 1;
> -             mmu = high;
> +             int high = (((unsigned long)virt_to_bus(memory) + size) & 
> ~dma_mask) != 0;
> +             int mmu = high;

Documentation/DMA-mapping.txt says consistent DMA mapping interface will always 
return SAC addressable DMA address. Your patch breaks this behavior.
(Though I don't know the reason why this behavior is expected!)

Appended is a simple 2.4 patch which will sync the behavior with 2.6

thanks,
suresh
--

Sync 2.4 pci_alloc_consistent behavior with 2.6

Signed-off-by: Suresh Siddha <[EMAIL PROTECTED]>


diff -Nru linux-2.4.29/arch/ia64/lib/swiotlb.c 
linux-2.4.29-swiotlb/arch/ia64/lib/swiotlb.c
--- linux-2.4.29/arch/ia64/lib/swiotlb.c        2003-08-25 04:44:39.000000000 
-0700
+++ linux-2.4.29-swiotlb/arch/ia64/lib/swiotlb.c        2005-03-22 
10:51:21.968565920 -0800
@@ -50,13 +50,13 @@
  * Used to do a quick range check in swiotlb_unmap_single and 
swiotlb_sync_single, to see
  * if the memory was in fact allocated by this API.
  */
-static char *io_tlb_start, *io_tlb_end;
+char *io_tlb_start, *io_tlb_end;
 
 /*
  * The number of IO TLB blocks (in groups of 64) betweeen io_tlb_start and 
io_tlb_end.
  * This is command line adjustable via setup_io_tlb_npages.
  */
-static unsigned long io_tlb_nslabs = 1024;
+static unsigned long io_tlb_nslabs = 32768;
 
 /*
  * This is a free list describing the number of free entries available from 
each index
diff -Nru linux-2.4.29/arch/x86_64/kernel/pci-gart.c 
linux-2.4.29-swiotlb/arch/x86_64/kernel/pci-gart.c
--- linux-2.4.29/arch/x86_64/kernel/pci-gart.c  2004-08-07 16:26:04.000000000 
-0700
+++ linux-2.4.29-swiotlb/arch/x86_64/kernel/pci-gart.c  2005-03-22 
10:38:45.211610464 -0800
@@ -155,7 +155,7 @@
        int i;
        unsigned long iommu_page;
 
-       if (hwdev == NULL || hwdev->dma_mask < 0xffffffff || no_iommu)
+       if (hwdev == NULL || hwdev->dma_mask < 0xffffffff || (no_iommu && 
!swiotlb))
                gfp |= GFP_DMA;
 
        /* 
@@ -174,6 +174,22 @@
                if (force_mmu && !(gfp & GFP_DMA)) 
                        mmu = 1;
                if (no_iommu) { 
+#ifdef CONFIG_SWIOTLB
+                       if (swiotlb && high && hwdev) {
+                               unsigned long dma_mask = 0;
+                               if (hwdev->dma_mask == ~0UL) {
+                                       hwdev->dma_mask = 0xffffffff;
+                                       dma_mask = ~0UL;
+                               }
+                               *dma_handle = swiotlb_map_single(hwdev, memory, 
size,
+                                                                
PCI_DMA_FROMDEVICE);
+                               if (dma_mask)
+                                       hwdev->dma_mask = dma_mask;
+                               memset(phys_to_virt(*dma_handle), 0, size); 
+                               free_pages((unsigned long)memory, 
get_order(size));
+                               return phys_to_virt(*dma_handle);
+                       }
+#endif
                        if (high) goto error;
                        mmu = 0; 
                }       
@@ -218,8 +234,16 @@
                         void *vaddr, dma_addr_t bus)
 {
        unsigned long iommu_page;
-
+       extern  char *io_tlb_start, *io_tlb_end;
+ 
        size = round_up(size, PAGE_SIZE); 
+#ifdef CONFIG_SWIOTLB
+       if (swiotlb && vaddr >= (void *)io_tlb_start &&
+           vaddr < (void *)io_tlb_end) {
+               swiotlb_unmap_single (hwdev, bus, size, PCI_DMA_TODEVICE);
+               return;
+       }
+#endif
        if (bus >= iommu_bus_base && bus < iommu_bus_base + iommu_size) { 
                unsigned pages = size >> PAGE_SHIFT;
                iommu_page = (bus - iommu_bus_base) >> PAGE_SHIFT;
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to