[Cbe-oss-dev] [PATCH 08/17]MARS/core: DMA api cleanup
Yuji Mano
yuji.mano at am.sony.com
Wed Dec 3 13:59:02 EST 2008
This patch cleans up the dma API.
All dma API is combined into a single mars_dma_get/put API that handles all
valid transfer sizes. The dma list command is currently no longer used.
Signed-off-by: Yuji Mano <yuji.mano at am.sony.com>
---
core/include/mpu/mars/dma.h | 387 ++++++--------------------------------------
1 file changed, 56 insertions(+), 331 deletions(-)
--- a/core/include/mpu/mars/dma.h
+++ b/core/include/mpu/mars/dma.h
@@ -57,83 +57,11 @@
#define MARS_DMA_SIZE_MASK 0xf
/* dma single tranfer size max 16KB */
#define MARS_DMA_SIZE_MAX 16384
-/* dma large transfer boundary max */
-#define MARS_DMA_LIST_BOUNDARY_MASK 0xffffffff00000000ULL
-/* dma list array size */
-#define MARS_DMA_LIST_SIZE 16
-/* dma large transfer size max */
-#define MARS_DMA_LARGE_SIZE_MAX (MARS_DMA_SIZE_MAX * MARS_DMA_LIST_SIZE)
#if defined(__cplusplus)
extern "C" {
#endif
-/* size max 16 KB */
-static inline unsigned int _list_init(mfc_list_element_t *list,
- unsigned int size, unsigned int eal)
-{
- unsigned int count = 0;
-
- while (size) {
- unsigned int block_size;
- block_size = (size < MARS_DMA_SIZE_MAX) ?
- size : MARS_DMA_SIZE_MAX;
- list[count].notify = 0;
- list[count].reserved = 0;
- list[count].size = block_size;
- list[count].eal = eal;
- size -= block_size;
- eal += block_size;
- count++;
- }
-
- return (count * sizeof(mfc_list_element_t));
-}
-
-static inline void _mars_dma_large_get(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- mfc_list_element_t list[MARS_DMA_LIST_SIZE] __attribute__((aligned(8)));
- unsigned int list_size;
- uint64_t ea2 = (ea + size - 1) & MARS_DMA_LIST_BOUNDARY_MASK;
-
- if (mfc_ea2h(ea) != mfc_ea2h(ea2)) {
- uint32_t size1 = ea2 - ea;
- uint32_t size2 = size - size1;
-
- list_size = _list_init(list, size1, mfc_ea2l(ea));
- mfc_getl((volatile void *)ls, ea, &list, list_size, tag, 0, 0);
-
- list_size = _list_init(list, size2, mfc_ea2l(ea2));
- mfc_getl((volatile void *)ls, ea2, &list, list_size, tag, 0, 0);
- } else {
- list_size = _list_init(list, size, mfc_ea2l(ea));
- mfc_getl((volatile void *)ls, ea, &list, list_size, tag, 0, 0);
- }
-}
-
-static inline void _mars_dma_large_put(const void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- mfc_list_element_t list[MARS_DMA_LIST_SIZE] __attribute__((aligned(8)));
- unsigned int list_size;
- uint64_t ea2 = (ea + size - 1) & MARS_DMA_LIST_BOUNDARY_MASK;
-
- if (mfc_ea2h(ea) != mfc_ea2h(ea2)) {
- uint32_t size1 = ea2 - ea;
- uint32_t size2 = size - size1;
-
- list_size = _list_init(list, size1, mfc_ea2l(ea));
- mfc_putl((volatile void *)ls, ea, &list, list_size, tag, 0, 0);
-
- list_size = _list_init(list, size2, mfc_ea2l(ea2));
- mfc_putl((volatile void *)ls, ea2, &list, list_size, tag, 0, 0);
- } else {
- list_size = _list_init(list, size, mfc_ea2l(ea));
- mfc_putl((volatile void *)ls, ea, &list, list_size, tag, 0, 0);
- }
-}
-
/*
* \ingroup group_mars_dma
* \brief [MPU] Waits for a dma transfer to complete.
@@ -141,8 +69,7 @@ static inline void _mars_dma_large_put(c
* This function will wait until all dma transfer operations currently
* initialized with the specified tag completes.
*
- * \param[in] tag - tag identifier of dma transfer to wait completion of\n
- * [between 0 and 31]
+ * \param[in] tag - tag identifier of dma transfer [between 0 and 31]
* \return
* none
*/
@@ -155,334 +82,132 @@ static inline void mars_dma_wait(uint32_
mfc_read_tag_status();
}
-static inline void mars_dma_sync(uint32_t tag)
-{
- assert(tag <= MARS_DMA_TAG_MAX);
-
- mfc_sync(tag);
-}
-
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts dma transfer from host storage to MPU storage.
- *
- * This function will start a dma transfer to copy the specified number of
- * bytes from host storage to MPU storage. This function should be used
- * when transferring data sizes between 16 bytes and 16 KB. For transfers
- * of sizes smaller than 16 bytes use \ref mars_dma_small_get. For transfers
- * of sizes larger than 16 KB use \ref mars_dma_large_get.
- *
- * \param[in] ls - address of MPU storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_get(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- assert(((uintptr_t)ls & MARS_DMA_ALIGN_MASK) == 0);
- assert(((uintptr_t)ea & MARS_DMA_ALIGN_MASK) == 0);
- assert((size & MARS_DMA_SIZE_MASK) == 0);
- assert(size && size <= MARS_DMA_SIZE_MAX);
- assert(tag <= MARS_DMA_TAG_MAX);
-
- mfc_get((volatile void *)ls, ea, size, tag, 0, 0);
-}
-
/*
* \ingroup group_mars_dma
- * \brief [MPU] Starts dma get operation and waits for completion.
+ * \brief [MPU] Syncs all dma requests with specified tag.
*
- * \param[in] ls - address of MPU storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_get_and_wait(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- mars_dma_get(ls, ea, size, tag);
- mars_dma_wait(tag);
-}
-
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts dma transfer from MPU storage to host storage.
+ * This function will wait until all dma requests with the specified tag are
+ * processed before continuing past the synchronization point.
*
- * This function will start a dma transfer to copy the specified number of
- * bytes from MPU storage to host storage. This function should be used
- * when transferring data sizes between 16 bytes and 16 KB. For transfers
- * of sizes smaller than 16 bytes use \ref mars_dma_small_get. For transfers
- * of sizes larger than 16 KB use \ref mars_dma_large_get.
- *
- * \param[in] ls - address of MPU storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
+ * \param[in] tag - tag identifier of dma transfer [between 0 and 31]
* \return
* none
*/
-static inline void mars_dma_put(const void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
+static inline void mars_dma_sync(uint32_t tag)
{
- assert(((uintptr_t)ls & MARS_DMA_ALIGN_MASK) == 0);
- assert(((uintptr_t)ea & MARS_DMA_ALIGN_MASK) == 0);
- assert((size & MARS_DMA_SIZE_MASK) == 0);
- assert(size && size <= MARS_DMA_SIZE_MAX);
assert(tag <= MARS_DMA_TAG_MAX);
- mfc_put((volatile void *)ls, ea, size, tag, 0, 0);
-}
-
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts dma put operation and waits for completion.
- *
- * \param[in] ls - address of MPU storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_put_and_wait(const void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- mars_dma_put(ls, ea, size, tag);
- mars_dma_wait(tag);
+ mfc_sync(tag);
}
/*
* \ingroup group_mars_dma
- * \brief [MPU] Starts small dma transfer from host storage to MPU storage.
+ * \brief [MPU] Starts dma transfer from host storage to MPU storage.
*
* This function will start a dma transfer to copy the specified number of
- * bytes from host storage to MPU storage. This function should be used
- * when transferring data sizes of 1, 2, 4, or 8 bytes. For transfers
- * of larger sizes use \ref mars_dma_get or \ref mars_dma_large_get.
+ * bytes from host storage to MPU storage.
*
- * \param[in] ls - address of MPU storage to transfer to
- * [lower 4 bits must be same as ea]
- * \param[in] ea - address of host storage to transfer from
- * [lower 4 bits must be same as ls]
+ * \param[in] ls - destination MPU storage address [16 byte aligned]
+ * \param[in] ea - source host storage address [16 byte aligned]
* \param[in] size - size of bytes to transfer
- * [1, 2, 4, or 8 bytes]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
+ * \param[in] tag - tag identifier of dma transfer [between 0 and 31]
* \return
* none
*/
-static inline void mars_dma_small_get(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
+static inline void mars_dma_get(void *ls, uint64_t ea,
+ uint32_t size, uint32_t tag)
{
assert(((uintptr_t)ls & MARS_DMA_ALIGN_MASK) == 0);
assert(((uintptr_t)ea & MARS_DMA_ALIGN_MASK) == 0);
- assert(size == 1 || size == 2 || size == 4 || size == 8);
+ assert(size == 1 || size == 2 || size == 4 || size == 8 ||
+ (size & MARS_DMA_SIZE_MASK) == 0);
+ assert(size && size <= MARS_DMA_LARGE_SIZE_MAX);
assert(tag <= MARS_DMA_TAG_MAX);
- mfc_get(ls, ea, size, tag, 0, 0);
-}
+ while (size) {
+ unsigned int block_size;
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts dma small get operation and waits for completion.
- *
- * \param[in] ls - address of MPU storage to transfer to
- * [lower 4 bits must be same as ea]
- * \param[in] ea - address of host storage to transfer from
- * [lower 4 bits must be same as ls]
- * \param[in] size - size of bytes to transfer
- * [1, 2, 4, or 8 bytes]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_small_get_and_wait(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- mars_dma_small_get(ls, ea, size, tag);
- mars_dma_wait(tag);
-}
+ block_size = (size < MARS_DMA_SIZE_MAX) ?
+ size : MARS_DMA_SIZE_MAX;
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts small dma transfer from MPU storage to host storage.
- *
- * This function will start a dma transfer to copy the specified number of
- * bytes from MPU storage to host storage. This function should be used
- * when transferring data sizes of 1, 2, 4, or 8 bytes. For transfers
- * of larger sizes use \ref mars_dma_get or \ref mars_dma_large_get.
- *
- * \param[in] ls - address of MPU storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_small_put(const void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- assert(((uintptr_t)ls & MARS_DMA_ALIGN_MASK) == 0);
- assert(((uintptr_t)ea & MARS_DMA_ALIGN_MASK) == 0);
- assert(size == 1 || size == 2 || size == 4 || size == 8);
- assert(tag <= MARS_DMA_TAG_MAX);
+ mfc_get((volatile void *)ls, ea, block_size, tag, 0, 0);
- mfc_put((volatile void *)ls, ea, size, tag, 0, 0);
+ ls += block_size;
+ ea += block_size;
+ size -= block_size;
+ }
}
/*
* \ingroup group_mars_dma
- * \brief [MPU] Starts dma small put operation and waits for completion.
+ * \brief [MPU] Starts dma get operation and waits for completion.
*
- * \param[in] ls - address of MPU storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer to
- * [aligned to a 16 byte address]
+ * \param[in] ls - destination MPU storage address [16 byte aligned]
+ * \param[in] ea - source host storage address [16 byte aligned]
* \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
+ * \param[in] tag - tag identifier of dma transfer [between 0 and 31]
* \return
* none
*/
-static inline void mars_dma_small_put_and_wait(const void *ls, uint64_t ea,
+static inline void mars_dma_get_and_wait(void *ls, uint64_t ea,
uint32_t size, uint32_t tag)
{
- mars_dma_small_put(ls, ea, size, tag);
+ mars_dma_get(ls, ea, size, tag);
mars_dma_wait(tag);
}
/*
* \ingroup group_mars_dma
- * \brief [MPU] Starts large dma transfer from host storage to MPU storage.
+ * \brief [MPU] Starts dma transfer from MPU storage to host storage.
*
* This function will start a dma transfer to copy the specified number of
- * bytes from host storage to MPU storage. This function should be used
- * when transferring data sizes of 16 KB and larger. This function can be
- * used for transfer sizes of 16KB and smaller, but for efficiency transfers
- * of smaller sizes should use \ref mars_dma_get or \ref mars_dma_small_get.
+ * bytes from MPU storage to host storage.
*
- * \param[in] ls - address of MPU storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer from
- * [aligned to a 16 byte address]
+ * \param[in] ls - source MPU storage address [16 byte aligned]
+ * \param[in] ea - destination host storage address [16 byte aligned]
* \param[in] size - size of bytes to transfer
- [16 KB and larger recommended]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
+ * \param[in] tag - tag identifier of dma transfer [between 0 and 31]
* \return
* none
*/
-static inline void mars_dma_large_get(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
+static inline void mars_dma_put(const void *ls, uint64_t ea,
+ uint32_t size, uint32_t tag)
{
assert(((uintptr_t)ls & MARS_DMA_ALIGN_MASK) == 0);
assert(((uintptr_t)ea & MARS_DMA_ALIGN_MASK) == 0);
- assert(size && size <= MARS_DMA_LARGE_SIZE_MAX);
+ assert(size == 1 || size == 2 || size == 4 || size == 8 ||
+ (size & MARS_DMA_SIZE_MASK) == 0);
assert(tag <= MARS_DMA_TAG_MAX);
- _mars_dma_large_get(ls, ea, size, tag);
-}
+ while (size) {
+ unsigned int block_size;
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts dma large get operation and waits for completion.
- *
- * \param[in] ls - address of MPU storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- [16 KB and larger recommended]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_large_get_and_wait(void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- mars_dma_large_get(ls, ea, size, tag);
- mars_dma_wait(tag);
-}
+ block_size = (size < MARS_DMA_SIZE_MAX) ?
+ size : MARS_DMA_SIZE_MAX;
-/*
- * \ingroup group_mars_dma
- * \brief [MPU] Starts large dma transfer from MPU storage to host storage.
- *
- * This function will start a dma transfer to copy the specified number of
- * bytes from MPU storage to host storage. This function should be used
- * when transferring data sizes of 16 KB and larger. This function can be
- * used for transfer sizes of 16KB and smaller, but for efficiency transfers
- * of smaller sizes should use \ref mars_dma_get or \ref mars_dma_small_get.
- *
- * \param[in] ls - address of MPU storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer to
- * [aligned to a 16 byte address]
- * \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
- * \return
- * none
- */
-static inline void mars_dma_large_put(const void *ls, uint64_t ea,
- uint32_t size, uint32_t tag)
-{
- assert(((uintptr_t)ls & MARS_DMA_ALIGN_MASK) == 0);
- assert(((uintptr_t)ea & MARS_DMA_ALIGN_MASK) == 0);
- assert(size && size <= MARS_DMA_LARGE_SIZE_MAX);
- assert(tag <= MARS_DMA_TAG_MAX);
+ mfc_put((volatile void *)ls, ea, block_size, tag, 0, 0);
- _mars_dma_large_put(ls, ea, size, tag);
+ ls += block_size;
+ ea += block_size;
+ size -= block_size;
+ }
}
/*
* \ingroup group_mars_dma
- * \brief [MPU] Starts dma large put operation and waits for completion.
+ * \brief [MPU] Starts dma put operation and waits for completion.
*
- * \param[in] ls - address of MPU storage to transfer from
- * [aligned to a 16 byte address]
- * \param[in] ea - address of host storage to transfer to
- * [aligned to a 16 byte address]
+ * \param[in] ls - source MPU storage address [16 byte aligned]
+ * \param[in] ea - destination host storage address [16 byte aligned]
* \param[in] size - size of bytes to transfer
- * [multiple of 16 bytes and no larger than 16 KB]
- * \param[in] tag - tag identifier of dma transfer
- * [between 0 and 31]
+ * \param[in] tag - tag identifier of dma transfer [between 0 and 31]
* \return
* none
*/
-static inline void mars_dma_large_put_and_wait(const void *ls, uint64_t ea,
+static inline void mars_dma_put_and_wait(const void *ls, uint64_t ea,
uint32_t size, uint32_t tag)
{
- mars_dma_large_put(ls, ea, size, tag);
+ mars_dma_put(ls, ea, size, tag);
mars_dma_wait(tag);
}
More information about the cbe-oss-dev
mailing list