From: Jens Axboe <[EMAIL PROTECTED]> Date: Thu, 18 Oct 2007 10:21:45 +0200
> I like it. Basically the only real change is using bit 2 as a > termination point, so we avoid going beyond the end of the sgtable. > Here's a starting point, it actually booted for me in the first go > (boggle). Only x86 so far, archs will need to be converted. And lots > more drivers I'm sure, I only fixed up the ones that botched my compile. > > So just consider this a directional patch. Here are some sparc64 bits: diff --git a/arch/sparc64/kernel/iommu.c b/arch/sparc64/kernel/iommu.c index 29af777..73852a2 100644 --- a/arch/sparc64/kernel/iommu.c +++ b/arch/sparc64/kernel/iommu.c @@ -473,7 +473,7 @@ static void dma_4u_unmap_single(struct device *dev, dma_addr_t bus_addr, } #define SG_ENT_PHYS_ADDRESS(SG) \ - (__pa(page_address((SG)->page)) + (SG)->offset) + (__pa(page_address(sg_page(SG))) + (SG)->offset) static void fill_sg(iopte_t *iopte, struct scatterlist *sg, int nused, int nelems, @@ -566,7 +566,7 @@ static int dma_4u_map_sg(struct device *dev, struct scatterlist *sglist, if (nelems == 1) { sglist->dma_address = dma_4u_map_single(dev, - (page_address(sglist->page) + + (page_address(sg_page(sglist)) + sglist->offset), sglist->length, direction); if (unlikely(sglist->dma_address == DMA_ERROR_CODE)) diff --git a/arch/sparc64/kernel/iommu_common.c b/arch/sparc64/kernel/iommu_common.c index d7ca900..ec863e0 100644 --- a/arch/sparc64/kernel/iommu_common.c +++ b/arch/sparc64/kernel/iommu_common.c @@ -73,7 +73,7 @@ static int verify_one_map(struct scatterlist *dma_sg, struct scatterlist **__sg, daddr = dma_sg->dma_address; sglen = sg->length; - sgaddr = (unsigned long) (page_address(sg->page) + sg->offset); + sgaddr = (unsigned long) (page_address(sg_page(sg)) + sg->offset); while (dlen > 0) { unsigned long paddr; @@ -123,7 +123,7 @@ static int verify_one_map(struct scatterlist *dma_sg, struct scatterlist **__sg, sg = sg_next(sg); if (--nents <= 0) break; - sgaddr = (unsigned long) (page_address(sg->page) + sg->offset); + sgaddr = (unsigned long) (page_address(sg_page(sg)) + sg->offset); sglen = sg->length; } if (dlen < 0) { @@ -191,7 +191,7 @@ void verify_sglist(struct scatterlist *sglist, int nents, iopte_t *iopte, int np printk("sg(%d): page_addr(%p) off(%x) length(%x) " "dma_address[%016x] dma_length[%016x]\n", i, - page_address(sg->page), sg->offset, + page_address(sg_page(sg)), sg->offset, sg->length, sg->dma_address, sg->dma_length); } @@ -207,15 +207,15 @@ unsigned long prepare_sg(struct scatterlist *sg, int nents) unsigned long prev; u32 dent_addr, dent_len; - prev = (unsigned long) (page_address(sg->page) + sg->offset); + prev = (unsigned long) (page_address(sg_page(sg)) + sg->offset); prev += (unsigned long) (dent_len = sg->length); - dent_addr = (u32) ((unsigned long)(page_address(sg->page) + sg->offset) + dent_addr = (u32) ((unsigned long)(page_address(sg_page(sg)) + sg->offset) & (IO_PAGE_SIZE - 1UL)); while (--nents) { unsigned long addr; sg = sg_next(sg); - addr = (unsigned long) (page_address(sg->page) + sg->offset); + addr = (unsigned long) (page_address(sg_page(sg)) + sg->offset); if (! VCONTIG(prev, addr)) { dma_sg->dma_address = dent_addr; dma_sg->dma_length = dent_len; diff --git a/arch/sparc64/kernel/pci_sun4v.c b/arch/sparc64/kernel/pci_sun4v.c index fe46ace..5324a34 100644 --- a/arch/sparc64/kernel/pci_sun4v.c +++ b/arch/sparc64/kernel/pci_sun4v.c @@ -366,7 +366,7 @@ static void dma_4v_unmap_single(struct device *dev, dma_addr_t bus_addr, } #define SG_ENT_PHYS_ADDRESS(SG) \ - (__pa(page_address((SG)->page)) + (SG)->offset) + (__pa(page_address(sg_page(SG))) + (SG)->offset) static long fill_sg(long entry, struct device *dev, struct scatterlist *sg, @@ -478,7 +478,7 @@ static int dma_4v_map_sg(struct device *dev, struct scatterlist *sglist, if (nelems == 1) { sglist->dma_address = dma_4v_map_single(dev, - (page_address(sglist->page) + + (page_address(sg_page(sglist)) + sglist->offset), sglist->length, direction); if (unlikely(sglist->dma_address == DMA_ERROR_CODE)) diff --git a/include/asm-sparc64/scatterlist.h b/include/asm-sparc64/scatterlist.h index 703c5bb..6df23f0 100644 --- a/include/asm-sparc64/scatterlist.h +++ b/include/asm-sparc64/scatterlist.h @@ -6,7 +6,10 @@ #include <asm/types.h> struct scatterlist { - struct page *page; +#ifdef CONFIG_DEBUG_SG + unsigned long sg_magic; +#endif + unsigned long page_link; unsigned int offset; unsigned int length; - 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/