lkml.org 
[lkml]   [2010]   [May]   [19]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    SubjectRe: [PATCH v3] ad7877: keep dma rx buffers in seperate cache lines
    From
    Date
    On Tue, 2010-05-11 at 16:54 -0400, Mike Frysinger wrote:
    >
    > > kmalloc returns a pointer to a DMA safe buffer. There is no requirement on
    > > the x86 hardware that the DMA buffers have to be cache aligned. Cachelines
    > > will be invalidated as needed.
    >
    > so this guarantee is made by the kmalloc() API ? and for arches where
    > the cacheline invalidation is handled in software rather than
    > hardware, they must declare a min alignment value for kmalloc to be at
    > least as big as their cache alignment ?
    >
    > does the phrase "DMA safe buffer" imply cache alignment ?

    Not necessarily. If you have cache-coherent DMA, then there's no need to
    align things. You only need cache-alignment when you have
    cache-incoherent DMA and have to manage the cache in software. And in
    that case, the architecture must set ARCH_KMALLOC_MINALIGN to an
    appropriate value so that kmalloc() meets the guarantee.

    However, your problem is kind of unrelated to that -- your problem is
    actually that you're putting both a DMA buffer _and_ other stuff into
    the same kmalloc'd buffer. Don't do that. Instead, allocate your DMA
    buffer separately and put a _pointer_ to it into the structure.

    Or if you really _must_ include it in your structure, then align to
    ARCH_KMALLOC_MINALIGN bytes both before and after the DMA buffer by
    adding __attribute__((__aligned__(ARCH_KMALLOC_MINALIGN))) to both the
    DMA buffer _and_ the element which follows it in your struct (if any).

    Using ____cacheline_aligned wastes a lot of space on the architectures
    that don't need it.

    Arguably, this __dma_aligned definition should go somewhere generic...

    diff --git a/drivers/input/touchscreen/ad7877.c b/drivers/input/touchscreen/ad7877.c
    index 0d2d7e5..ae5d56e 100644
    --- a/drivers/input/touchscreen/ad7877.c
    +++ b/drivers/input/touchscreen/ad7877.c
    @@ -151,6 +151,11 @@ enum {
    /*
    * Non-touchscreen sensors only use single-ended conversions.
    */
    +#ifdef ARCH_KMALLOC_MINALIGN
    +#define __dma_aligned __attribute__((__aligned__(ARCH_KMALLOC_MINALIGN)))
    +#else
    +#define __dma_aligned
    +#endif

    struct ser_req {
    u16 reset;
    @@ -163,7 +168,7 @@ struct ser_req {
    * DMA (thus cache coherency maintenance) requires the
    * transfer buffers to live in their own cache lines.
    */
    - u16 sample ____cacheline_aligned;
    + u16 sample __dma_aligned;
    };

    struct ad7877 {
    @@ -203,7 +208,7 @@ struct ad7877 {
    * DMA (thus cache coherency maintenance) requires the
    * transfer buffers to live in their own cache lines.
    */
    - u16 conversion_data[AD7877_NR_SENSE] ____cacheline_aligned;
    + u16 conversion_data[AD7877_NR_SENSE] __dma_aligned;
    };

    static int gpio3;

    --
    David Woodhouse Open Source Technology Centre
    David.Woodhouse@intel.com Intel Corporation



    \
     
     \ /
      Last update: 2010-05-19 15:03    [W:4.031 / U:0.660 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site