summaryrefslogtreecommitdiffstats
path: root/dma
diff options
context:
space:
mode:
authorSuren A. Chilingaryan <csa@suren.me>2015-04-20 22:01:04 +0200
committerSuren A. Chilingaryan <csa@suren.me>2015-04-20 22:01:04 +0200
commit77c4d6e67debf0e729734d882df033c4c0f5b0c3 (patch)
tree4a59e86332d6cc78fc5c97110ecba281b0f67bc9 /dma
parent0002c0cc260a6a8e2b6c53f19ae99a625eca4355 (diff)
downloadpcitool-77c4d6e67debf0e729734d882df033c4c0f5b0c3.tar.gz
pcitool-77c4d6e67debf0e729734d882df033c4c0f5b0c3.tar.bz2
pcitool-77c4d6e67debf0e729734d882df033c4c0f5b0c3.tar.xz
pcitool-77c4d6e67debf0e729734d882df033c4c0f5b0c3.zip
Big redign of model structures
Diffstat (limited to 'dma')
-rw-r--r--dma/CMakeLists.txt6
-rw-r--r--dma/ipe.c83
-rw-r--r--dma/ipe.h61
-rw-r--r--dma/ipe_private.h10
-rw-r--r--dma/ipe_registers.h44
-rw-r--r--dma/nwl.c115
-rw-r--r--dma/nwl.h101
-rw-r--r--dma/nwl_engine.c136
-rw-r--r--dma/nwl_engine.h2
-rw-r--r--dma/nwl_engine_buffers.h200
-rw-r--r--dma/nwl_irq.c10
-rw-r--r--dma/nwl_irq.h6
-rw-r--r--dma/nwl_loopback.c44
-rw-r--r--dma/nwl_loopback.h6
-rw-r--r--dma/nwl_private.h32
-rw-r--r--dma/nwl_register.c77
-rw-r--r--dma/nwl_register.h97
17 files changed, 498 insertions, 532 deletions
diff --git a/dma/CMakeLists.txt b/dma/CMakeLists.txt
index 44bf18c..9bbfacd 100644
--- a/dma/CMakeLists.txt
+++ b/dma/CMakeLists.txt
@@ -3,7 +3,9 @@ include_directories(
)
-set(HEADERS ${HEADERS} nwl.h nwl_private.h nwl_engine.h nwl_irq.h nwl_loopback.h nwl_register.h ipe.h ipe_private.h ipe_registers.h)
+set(HEADERS ${HEADERS} nwl.h nwl_private.h nwl_engine.h nwl_irq.h nwl_loopback.h ipe.h ipe_private.h)
-add_library(dma STATIC nwl.c nwl_engine.c nwl_irq.c nwl_loopback.c nwl_register.c ipe.c)
+add_library(dma STATIC nwl.c nwl_engine.c nwl_irq.c nwl_loopback.c ipe.c)
+#set(HEADERS ${HEADERS} ipe.h ipe_private.h)
+#add_library(dma STATIC ipe.c)
diff --git a/dma/ipe.c b/dma/ipe.c
index b692e0d..e7a292a 100644
--- a/dma/ipe.c
+++ b/dma/ipe.c
@@ -15,25 +15,25 @@
#include "ipe.h"
#include "ipe_private.h"
-#include "ipe_registers.h"
#define WR(addr, value) { *(uint32_t*)(ctx->base_addr + addr) = value; }
#define RD(addr, value) { value = *(uint32_t*)(ctx->base_addr + addr); }
-pcilib_dma_context_t *dma_ipe_init(pcilib_t *pcilib, pcilib_dma_modification_t type, void *arg) {
- int err = 0;
+pcilib_dma_context_t *dma_ipe_init(pcilib_t *pcilib, const char *model, const void *arg) {
+// int err = 0;
- pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
+ const pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
ipe_dma_t *ctx = malloc(sizeof(ipe_dma_t));
if (ctx) {
memset(ctx, 0, sizeof(ipe_dma_t));
- ctx->pcilib = pcilib;
+ ctx->dmactx.pcilib = pcilib;
// ctx->mode64 = 1;
-
+
+/*
memset(ctx->engine, 0, 2 * sizeof(pcilib_dma_engine_description_t));
ctx->engine[0].addr = 0;
ctx->engine[0].type = PCILIB_DMA_TYPE_PACKET;
@@ -41,8 +41,21 @@ pcilib_dma_context_t *dma_ipe_init(pcilib_t *pcilib, pcilib_dma_modification_t t
ctx->engine[0].addr_bits = 32;
pcilib_set_dma_engine_description(pcilib, 0, &ctx->engine[0]);
pcilib_set_dma_engine_description(pcilib, 1, NULL);
+*/
+
+ pcilib_register_bank_t dma_bank = pcilib_find_register_bank_by_addr(pcilib, PCILIB_REGISTER_BANK_DMA);
+/*
+ if (dma_bank == PCILIB_REGISTER_BANK_INVALID) {
+ err = pcilib_add_register_banks(ctx->pcilib, 0, ipe_dma_register_banks);
+ if (err) {
+ free(ctx);
+ pcilib_error("Error (%i) adding DMA register bank");
+ return NULL;
+ }
+ }
- pcilib_register_bank_t dma_bank = pcilib_find_bank_by_addr(pcilib, PCILIB_REGISTER_BANK_DMA);
+ dma_bank = pcilib_find_bank_by_addr(pcilib, PCILIB_REGISTER_BANK_DMA);
+*/
if (dma_bank == PCILIB_REGISTER_BANK_INVALID) {
free(ctx);
pcilib_error("DMA Register Bank could not be found");
@@ -52,12 +65,14 @@ pcilib_dma_context_t *dma_ipe_init(pcilib_t *pcilib, pcilib_dma_modification_t t
ctx->dma_bank = model_info->banks + dma_bank;
ctx->base_addr = pcilib_resolve_register_address(pcilib, ctx->dma_bank->bar, ctx->dma_bank->read_addr);
+/*
err = pcilib_add_registers(ctx->pcilib, 0, ipe_dma_registers);
if (err) {
free(ctx);
pcilib_error("Error adding DMA registers");
return NULL;
}
+*/
}
return (pcilib_dma_context_t*)ctx;
@@ -100,16 +115,16 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
if (ctx->pages) return 0;
kflags = PCILIB_KMEM_FLAG_REUSE|PCILIB_KMEM_FLAG_EXCLUSIVE|PCILIB_KMEM_FLAG_HARDWARE|(ctx->preserve?PCILIB_KMEM_FLAG_PERSISTENT:0);
- pcilib_kmem_handle_t *desc = pcilib_alloc_kernel_memory(ctx->pcilib, PCILIB_KMEM_TYPE_CONSISTENT, 1, IPEDMA_DESCRIPTOR_SIZE, IPEDMA_DESCRIPTOR_ALIGNMENT, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_RING, 0x00), kflags);
- pcilib_kmem_handle_t *pages = pcilib_alloc_kernel_memory(ctx->pcilib, PCILIB_KMEM_TYPE_DMA_C2S_PAGE, IPEDMA_DMA_PAGES, 0, 0, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_PAGES, 0x00), kflags);
+ pcilib_kmem_handle_t *desc = pcilib_alloc_kernel_memory(ctx->dmactx.pcilib, PCILIB_KMEM_TYPE_CONSISTENT, 1, IPEDMA_DESCRIPTOR_SIZE, IPEDMA_DESCRIPTOR_ALIGNMENT, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_RING, 0x00), kflags);
+ pcilib_kmem_handle_t *pages = pcilib_alloc_kernel_memory(ctx->dmactx.pcilib, PCILIB_KMEM_TYPE_DMA_C2S_PAGE, IPEDMA_DMA_PAGES, 0, 0, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_PAGES, 0x00), kflags);
if (!desc||!pages) {
- if (pages) pcilib_free_kernel_memory(ctx->pcilib, pages, 0);
- if (desc) pcilib_free_kernel_memory(ctx->pcilib, desc, 0);
+ if (pages) pcilib_free_kernel_memory(ctx->dmactx.pcilib, pages, 0);
+ if (desc) pcilib_free_kernel_memory(ctx->dmactx.pcilib, desc, 0);
return PCILIB_ERROR_MEMORY;
}
- reuse_desc = pcilib_kmem_is_reused(ctx->pcilib, desc);
- reuse_pages = pcilib_kmem_is_reused(ctx->pcilib, pages);
+ reuse_desc = pcilib_kmem_is_reused(ctx->dmactx.pcilib, desc);
+ reuse_pages = pcilib_kmem_is_reused(ctx->dmactx.pcilib, pages);
if (reuse_desc == reuse_pages) {
if (reuse_desc & PCILIB_KMEM_REUSE_PARTIAL) pcilib_warning("Inconsistent DMA buffers are found (only part of required buffers is available), reinitializing...");
@@ -128,7 +143,7 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
}
} else pcilib_warning("Inconsistent DMA buffers (modes of ring and page buffers does not match), reinitializing....");
- desc_va = pcilib_kmem_get_ua(ctx->pcilib, desc);
+ desc_va = pcilib_kmem_get_ua(ctx->dmactx.pcilib, desc);
if (ctx->mode64) last_written_addr_ptr = desc_va + 3 * sizeof(uint32_t);
else last_written_addr_ptr = desc_va + 4 * sizeof(uint32_t);
@@ -186,14 +201,14 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
// Setting current read position and configuring progress register
WR(IPEDMA_REG_LAST_READ, IPEDMA_DMA_PAGES);
- WR(IPEDMA_REG_UPDATE_ADDR, pcilib_kmem_get_block_ba(ctx->pcilib, desc, 0));
+ WR(IPEDMA_REG_UPDATE_ADDR, pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, desc, 0));
// Instructing DMA engine that writting should start from the first DMA page
- *last_written_addr_ptr = 0;//htonl(pcilib_kmem_get_block_ba(ctx->pcilib, pages, IPEDMA_DMA_PAGES - 1));
+ *last_written_addr_ptr = 0;//htonl(pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, pages, IPEDMA_DMA_PAGES - 1));
for (i = 0; i < IPEDMA_DMA_PAGES; i++) {
- uintptr_t bus_addr_check, bus_addr = pcilib_kmem_get_block_ba(ctx->pcilib, pages, i);
+ uintptr_t bus_addr_check, bus_addr = pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, pages, i);
WR(IPEDMA_REG_PAGE_ADDR, bus_addr);
if (bus_addr%4096) printf("Bad address %lu: %lx\n", i, bus_addr);
@@ -219,13 +234,13 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
#endif /* IPEDMA_BUG_DMARD */
}
-// ctx->last_read_addr = htonl(pcilib_kmem_get_block_ba(ctx->pcilib, pages, ctx->last_read));
- ctx->last_read_addr = pcilib_kmem_get_block_ba(ctx->pcilib, pages, ctx->last_read);
+// ctx->last_read_addr = htonl(pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, pages, ctx->last_read));
+ ctx->last_read_addr = pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, pages, ctx->last_read);
ctx->desc = desc;
ctx->pages = pages;
- ctx->page_size = pcilib_kmem_get_block_size(ctx->pcilib, pages, 0);;
+ ctx->page_size = pcilib_kmem_get_block_size(ctx->dmactx.pcilib, pages, 0);;
ctx->ring_size = IPEDMA_DMA_PAGES;
return 0;
@@ -269,12 +284,12 @@ int dma_ipe_stop(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma
// Clean buffers
if (ctx->desc) {
- pcilib_free_kernel_memory(ctx->pcilib, ctx->desc, kflags);
+ pcilib_free_kernel_memory(ctx->dmactx.pcilib, ctx->desc, kflags);
ctx->desc = NULL;
}
if (ctx->pages) {
- pcilib_free_kernel_memory(ctx->pcilib, ctx->pages, kflags);
+ pcilib_free_kernel_memory(ctx->dmactx.pcilib, ctx->pages, kflags);
ctx->pages = NULL;
}
@@ -286,7 +301,7 @@ int dma_ipe_get_status(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcil
size_t i;
ipe_dma_t *ctx = (ipe_dma_t*)vctx;
- void *desc_va = (void*)pcilib_kmem_get_ua(ctx->pcilib, ctx->desc);
+ void *desc_va = (void*)pcilib_kmem_get_ua(ctx->dmactx.pcilib, ctx->desc);
uint32_t *last_written_addr_ptr;
uint32_t last_written_addr;
@@ -307,7 +322,7 @@ int dma_ipe_get_status(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcil
// Find where the ring head is actually are
for (i = 0; i < ctx->ring_size; i++) {
- uintptr_t bus_addr = pcilib_kmem_get_block_ba(ctx->pcilib, ctx->pages, i);
+ uintptr_t bus_addr = pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, ctx->pages, i);
if (bus_addr == last_written_addr) {
status->ring_head = bus_addr;
@@ -373,7 +388,7 @@ int dma_ipe_stream_read(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, uin
err = dma_ipe_start(vctx, dma, PCILIB_DMA_FLAGS_DEFAULT);
if (err) return err;
- desc_va = (void*)pcilib_kmem_get_ua(ctx->pcilib, ctx->desc);
+ desc_va = (void*)pcilib_kmem_get_ua(ctx->dmactx.pcilib, ctx->desc);
if (ctx->mode64) last_written_addr_ptr = desc_va + 3 * sizeof(uint32_t);
else last_written_addr_ptr = desc_va + 4 * sizeof(uint32_t);
@@ -428,24 +443,24 @@ int dma_ipe_stream_read(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, uin
#endif /* IPEDMA_DEBUG */
#ifdef IPEDMA_DETECT_PACKETS
- if ((*empty_detected_ptr)&&(pcilib_kmem_get_block_ba(ctx->pcilib, ctx->pages, cur_read) == (*last_written_addr_ptr))) packet_flags = PCILIB_DMA_FLAG_EOP;
+ if ((*empty_detected_ptr)&&(pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, ctx->pages, cur_read) == (*last_written_addr_ptr))) packet_flags = PCILIB_DMA_FLAG_EOP;
else packet_flags = 0;
#endif /* IPEDMA_DETECT_PACKETS */
- pcilib_kmem_sync_block(ctx->pcilib, ctx->pages, PCILIB_KMEM_SYNC_FROMDEVICE, cur_read);
- void *buf = pcilib_kmem_get_block_ua(ctx->pcilib, ctx->pages, cur_read);
+ pcilib_kmem_sync_block(ctx->dmactx.pcilib, ctx->pages, PCILIB_KMEM_SYNC_FROMDEVICE, cur_read);
+ void *buf = pcilib_kmem_get_block_ua(ctx->dmactx.pcilib, ctx->pages, cur_read);
ret = cb(cbattr, packet_flags, ctx->page_size, buf);
if (ret < 0) return -ret;
// DS: Fixme, it looks like we can avoid calling this for the sake of performance
-// pcilib_kmem_sync_block(ctx->pcilib, ctx->pages, PCILIB_KMEM_SYNC_TODEVICE, cur_read);
+// pcilib_kmem_sync_block(ctx->dmactx.pcilib, ctx->pages, PCILIB_KMEM_SYNC_TODEVICE, cur_read);
// Numbered from 1
WR(IPEDMA_REG_LAST_READ, cur_read + 1);
ctx->last_read = cur_read;
-// ctx->last_read_addr = htonl(pcilib_kmem_get_block_ba(ctx->pcilib, ctx->pages, cur_read));
- ctx->last_read_addr = pcilib_kmem_get_block_ba(ctx->pcilib, ctx->pages, cur_read);
+// ctx->last_read_addr = htonl(pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, ctx->pages, cur_read));
+ ctx->last_read_addr = pcilib_kmem_get_block_ba(ctx->dmactx.pcilib, ctx->pages, cur_read);
#ifdef IPEDMA_BUG_DMARD
FILE *f = fopen("/tmp/pcitool_lastread", "w");
@@ -481,7 +496,7 @@ double dma_ipe_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
WR(IPEDMA_REG_CONTROL, 0x0);
- err = pcilib_skip_dma(ctx->pcilib, 0);
+ err = pcilib_skip_dma(ctx->dmactx.pcilib, 0);
if (err) {
pcilib_error("Can't start benchmark, devices continuously writes unexpected data using DMA engine");
return -1;
@@ -500,7 +515,7 @@ double dma_ipe_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
WR(IPEDMA_REG_CONTROL, 0x1);
for (bytes = 0; bytes < size; bytes += rbytes) {
- err = pcilib_read_dma(ctx->pcilib, 0, addr, size - bytes, buf + bytes, &rbytes);
+ err = pcilib_read_dma(ctx->dmactx.pcilib, 0, addr, size - bytes, buf + bytes, &rbytes);
if (err) {
pcilib_error("Can't read data from DMA, error %i", err);
return -1;
@@ -514,7 +529,7 @@ double dma_ipe_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
gettimeofday(&cur, NULL);
us += ((cur.tv_sec - start.tv_sec)*1000000 + (cur.tv_usec - start.tv_usec));
- err = pcilib_skip_dma(ctx->pcilib, 0);
+ err = pcilib_skip_dma(ctx->dmactx.pcilib, 0);
if (err) {
pcilib_error("Can't start iteration, devices continuously writes unexpected data using DMA engine");
break;
diff --git a/dma/ipe.h b/dma/ipe.h
index 2c34ff1..208911a 100644
--- a/dma/ipe.h
+++ b/dma/ipe.h
@@ -6,22 +6,19 @@
//#define PCILIB_NWL_MODIFICATION_IPECAMERA 0x100
-pcilib_dma_context_t *dma_ipe_init(pcilib_t *ctx, pcilib_dma_modification_t type, void *arg);
+pcilib_dma_context_t *dma_ipe_init(pcilib_t *ctx, const char *model, const void *arg);
void dma_ipe_free(pcilib_dma_context_t *vctx);
int dma_ipe_get_status(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma_engine_status_t *status, size_t n_buffers, pcilib_dma_buffer_status_t *buffers);
-
int dma_ipe_start(pcilib_dma_context_t *ctx, pcilib_dma_engine_t dma, pcilib_dma_flags_t flags);
int dma_ipe_stop(pcilib_dma_context_t *ctx, pcilib_dma_engine_t dma, pcilib_dma_flags_t flags);
int dma_ipe_stream_read(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, uintptr_t addr, size_t size, pcilib_dma_flags_t flags, pcilib_timeout_t timeout, pcilib_dma_callback_t cb, void *cbattr);
double dma_ipe_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dma, uintptr_t addr, size_t size, size_t iterations, pcilib_dma_direction_t direction);
-
-#ifdef _PCILIB_DMA_IPE_C
-pcilib_dma_api_description_t ipe_dma_api = {
- "ipe_dma",
+#ifdef _PCILIB_CONFIG_C
+static const pcilib_dma_api_description_t ipe_dma_api = {
dma_ipe_init,
dma_ipe_free,
dma_ipe_get_status,
@@ -34,9 +31,55 @@ pcilib_dma_api_description_t ipe_dma_api = {
dma_ipe_stream_read,
dma_ipe_benchmark
};
-#else
-extern pcilib_dma_api_description_t ipe_dma_api;
-#endif
+
+static const pcilib_dma_engine_description_t ipe_dma_engines[] = {
+ { 0, PCILIB_DMA_TYPE_PACKET, PCILIB_DMA_FROM_DEVICE, 32, "dma", NULL },
+ { 0 }
+};
+
+static const pcilib_register_bank_description_t ipe_dma_banks[] = {
+ { PCILIB_REGISTER_BANK_DMA, PCILIB_BAR0, 0xA000, PCILIB_REGISTER_PROTOCOL_DEFAULT, 0, 0, PCILIB_LITTLE_ENDIAN, 32, PCILIB_LITTLE_ENDIAN, "0x%lx", "dma", "DMA Registers"},
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, NULL, NULL, NULL }
+};
+
+static const pcilib_register_description_t ipe_dma_registers[] = {
+ {0x0000, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dcr", "Device Control Status Register"},
+ {0x0000, 0, 1, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "reset_dma", ""},
+ {0x0000, 16, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "datapath_width", ""},
+ {0x0000, 24, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "fpga_family", ""},
+ {0x0004, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "ddmacr", "Device DMA Control Status Register"},
+ {0x0004, 0, 1, 0, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_start", "Start writting memory"},
+ {0x0004, 5, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_relxed_order", ""},
+ {0x0004, 6, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_nosnoop", ""},
+ {0x0004, 7, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_int_dis", ""},
+ {0x0004, 16, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_start", ""},
+ {0x0004, 21, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_relaxed_order", ""},
+ {0x0004, 22, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_nosnoop", ""},
+ {0x0004, 23, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_int_dis", ""},
+ {0x000C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_size", "DMA TLP size"},
+ {0x000C, 0, 16, 0x20, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_len", "Max TLP size"},
+ {0x000C, 16, 3, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_tlp_tc", "TC for TLP packets"},
+ {0x000C, 19, 1, 0, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_64b_en", "Enable 64 bit memory addressing"},
+ {0x000C, 20, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_phant_func_dis", "Disable MWR phantom function"},
+ {0x000C, 24, 8, 0, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_up_addr", "Upper address for 64 bit memory addressing"},
+ {0x0010, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_count", "Write DMA TLP Count"},
+ {0x0014, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_pattern", "DMA generator data pattern"},
+ {0x0028, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_perf", "MWR Performance"},
+ {0x003C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "cfg_lnk_width", "Negotiated and max width of PCIe Link"},
+ {0x003C, 0, 6, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_cap_max_lnk_width", "Max link width"},
+ {0x003C, 8, 6, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_prg_max_lnk_width", "Negotiated link width"},
+ {0x0040, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "cfg_payload_size", ""},
+ {0x0040, 0, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_cap_max_payload_size", "Max payload size"},
+ {0x0040, 8, 3, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_prg_max_payload_size", "Prog max payload size"},
+ {0x0040, 16, 3, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_max_rd_req_size", "Max read request size"},
+ {0x0050, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "desc_mem_din", "Descriptor memory"},
+ {0x0054, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "update_addr", "Address of progress register"},
+ {0x0058, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "last_descriptor_read", "Last descriptor read by the host"},
+ {0x005C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "desc_mem_addr", "Number of descriptors configured"},
+ {0x0060, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "update_thresh", "Update threshold of progress register"},
+ {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
+};
+#endif /* _PCILIB_CONFIG_C */
#endif /* _PCILIB_DMA_IPE_H */
diff --git a/dma/ipe_private.h b/dma/ipe_private.h
index fd44011..161e609 100644
--- a/dma/ipe_private.h
+++ b/dma/ipe_private.h
@@ -1,6 +1,8 @@
#ifndef _PCILIB_DMA_IPE_PRIVATE_H
#define _PCILIB_DMA_IPE_PRIVATE_H
+#include "dma.h"
+
#define IPEDMA_CORES 1
#define IPEDMA_TLP_SIZE 32
#define IPEDMA_PAGE_SIZE 4096
@@ -30,12 +32,10 @@
typedef struct ipe_dma_s ipe_dma_t;
struct ipe_dma_s {
- struct pcilib_dma_context_s dmactx;
- pcilib_dma_engine_description_t engine[2];
+ pcilib_dma_context_t dmactx;
+ //pcilib_dma_engine_description_t engine[2];
- pcilib_t *pcilib;
-
- pcilib_register_bank_description_t *dma_bank;
+ const pcilib_register_bank_description_t *dma_bank;
char *base_addr;
pcilib_irq_type_t irq_enabled; /**< indicates that IRQs are enabled */
diff --git a/dma/ipe_registers.h b/dma/ipe_registers.h
deleted file mode 100644
index 17fc41a..0000000
--- a/dma/ipe_registers.h
+++ /dev/null
@@ -1,44 +0,0 @@
-#ifndef _PCILIB_DMA_IPE_REGISTERS_H
-#define _PCILIB_DMA_IPE_REGISTERS_H
-
-#ifdef _PCILIB_DMA_IPE_C
-static pcilib_register_description_t ipe_dma_registers[] = {
- {0x0000, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dcr", "Device Control Status Register"},
- {0x0000, 0, 1, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "reset_dma", ""},
- {0x0000, 16, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "datapath_width", ""},
- {0x0000, 24, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "fpga_family", ""},
- {0x0004, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "ddmacr", "Device DMA Control Status Register"},
- {0x0004, 0, 1, 0, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_start", "Start writting memory"},
- {0x0004, 5, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_relxed_order", ""},
- {0x0004, 6, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_nosnoop", ""},
- {0x0004, 7, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_int_dis", ""},
- {0x0004, 16, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_start", ""},
- {0x0004, 21, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_relaxed_order", ""},
- {0x0004, 22, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_nosnoop", ""},
- {0x0004, 23, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mrd_int_dis", ""},
- {0x000C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_size", "DMA TLP size"},
- {0x000C, 0, 16, 0x20, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_len", "Max TLP size"},
- {0x000C, 16, 3, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_tlp_tc", "TC for TLP packets"},
- {0x000C, 19, 1, 0, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_64b_en", "Enable 64 bit memory addressing"},
- {0x000C, 20, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_phant_func_dis", "Disable MWR phantom function"},
- {0x000C, 24, 8, 0, 0xFFFFFFFF, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "mwr_up_addr", "Upper address for 64 bit memory addressing"},
- {0x0010, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_count", "Write DMA TLP Count"},
- {0x0014, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_pattern", "DMA generator data pattern"},
- {0x0028, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "mwr_perf", "MWR Performance"},
- {0x003C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "cfg_lnk_width", "Negotiated and max width of PCIe Link"},
- {0x003C, 0, 6, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_cap_max_lnk_width", "Max link width"},
- {0x003C, 8, 6, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_prg_max_lnk_width", "Negotiated link width"},
- {0x0040, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "cfg_payload_size", ""},
- {0x0040, 0, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_cap_max_payload_size", "Max payload size"},
- {0x0040, 8, 3, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_prg_max_payload_size", "Prog max payload size"},
- {0x0040, 16, 3, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "cfg_max_rd_req_size", "Max read request size"},
- {0x0050, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "desc_mem_din", "Descriptor memory"},
- {0x0054, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "update_addr", "Address of progress register"},
- {0x0058, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "last_descriptor_read", "Last descriptor read by the host"},
- {0x005C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "desc_mem_addr", "Number of descriptors configured"},
- {0x0060, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "update_thresh", "Update threshold of progress register"},
- {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
-};
-#endif /* _PCILIB_DMA_IPE_C */
-
-#endif /* _PCILIB_DMA_IPE_REGISTERS_H */
diff --git a/dma/nwl.c b/dma/nwl.c
index 52b46ef..d22df29 100644
--- a/dma/nwl.c
+++ b/dma/nwl.c
@@ -1,5 +1,6 @@
#define _PCILIB_DMA_NWL_C
#define _BSD_SOURCE
+#define _GNU_SOURCE
#include <stdio.h>
#include <stdlib.h>
@@ -11,8 +12,8 @@
#include "pcilib.h"
#include "error.h"
#include "tools.h"
-#include "nwl_private.h"
+#include "nwl_private.h"
#include "nwl_defines.h"
int dma_nwl_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma_flags_t flags) {
@@ -25,7 +26,7 @@ int dma_nwl_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
}
if (dma == PCILIB_DMA_ENGINE_INVALID) return 0;
- else if (dma > ctx->n_engines) return PCILIB_ERROR_INVALID_BANK;
+ else if (dma > ctx->dmactx.pcilib->num_engines) return PCILIB_ERROR_INVALID_BANK;
if (flags&PCILIB_DMA_FLAG_PERSISTENT) ctx->engines[dma].preserve = 1;
@@ -44,7 +45,7 @@ int dma_nwl_stop(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma
// stop everything
if (dma == PCILIB_DMA_ENGINE_INVALID) {
- for (dma = 0; dma < ctx->n_engines; dma++) {
+ for (dma = 0; dma < ctx->dmactx.pcilib->num_engines; dma++) {
if (flags&PCILIB_DMA_FLAG_PERSISTENT) {
ctx->engines[dma].preserve = 0;
}
@@ -63,7 +64,7 @@ int dma_nwl_stop(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma
return 0;
}
- if (dma > ctx->n_engines) return PCILIB_ERROR_INVALID_BANK;
+ if (dma > ctx->dmactx.pcilib->num_engines) return PCILIB_ERROR_INVALID_BANK;
// ignorign previous setting if flag specified
if (flags&PCILIB_DMA_FLAG_PERSISTENT) {
@@ -74,55 +75,99 @@ int dma_nwl_stop(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma
}
-pcilib_dma_context_t *dma_nwl_init(pcilib_t *pcilib, pcilib_dma_modification_t type, void *arg) {
- int i;
+pcilib_dma_context_t *dma_nwl_init(pcilib_t *pcilib, const char *model, const void *arg) {
+ int i, j;
int err;
- pcilib_dma_engine_t n_engines;
-
- pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
+
+ pcilib_dma_engine_t dma;
+ pcilib_register_description_t eregs[NWL_MAX_DMA_ENGINE_REGISTERS];
+ const pcilib_model_description_t *model_info = pcilib_get_model_description(pcilib);
nwl_dma_t *ctx = malloc(sizeof(nwl_dma_t));
- if (ctx) {
- memset(ctx, 0, sizeof(nwl_dma_t));
- ctx->pcilib = pcilib;
- ctx->type = type;
+ if (!ctx) return NULL;
- if (type == PCILIB_NWL_MODIFICATION_IPECAMERA) {
- ctx->dmactx.ignore_eop = 1;
- }
+ memset(ctx, 0, sizeof(nwl_dma_t));
+
+ pcilib_register_bank_t dma_bank = pcilib_find_register_bank_by_addr(pcilib, PCILIB_REGISTER_BANK_DMA);
+ if (dma_bank == PCILIB_REGISTER_BANK_INVALID) {
+ free(ctx);
+ pcilib_error("DMA Register Bank could not be found");
+ return NULL;
+ }
- pcilib_register_bank_t dma_bank = pcilib_find_bank_by_addr(pcilib, PCILIB_REGISTER_BANK_DMA);
- if (dma_bank == PCILIB_REGISTER_BANK_INVALID) {
+ ctx->dma_bank = model_info->banks + dma_bank;
+ ctx->base_addr = pcilib_resolve_register_address(pcilib, ctx->dma_bank->bar, ctx->dma_bank->read_addr);
+
+ if ((model)&&(strcasestr(model, "ipecamera"))) {
+ ctx->type = NWL_MODIFICATION_IPECAMERA;
+ ctx->ignore_eop = 1;
+ } else {
+ ctx->type = NWL_MODIFICATION_DEFAULT;
+
+ err = pcilib_add_registers(pcilib, 0, nwl_xrawdata_registers);
+ if (err) {
free(ctx);
- pcilib_error("DMA Register Bank could not be found");
+ pcilib_error("Error (%i) adding NWL XRAWDATA registers", err);
return NULL;
}
-
- ctx->dma_bank = model_info->banks + dma_bank;
- ctx->base_addr = pcilib_resolve_register_address(pcilib, ctx->dma_bank->bar, ctx->dma_bank->read_addr);
+ }
- for (i = 0, n_engines = 0; i < 2 * PCILIB_MAX_DMA_ENGINES; i++) {
- char *addr = ctx->base_addr + DMA_OFFSET + i * DMA_ENGINE_PER_SIZE;
+ for (j = 0; nwl_dma_engine_registers[j].bits; j++);
+ if (j > NWL_MAX_DMA_ENGINE_REGISTERS) {
+ free(ctx);
+ pcilib_error("Too many (%i) engine registers defined, only %i supported", j, NWL_MAX_DMA_ENGINE_REGISTERS);
+ return NULL;
+ }
+
+ memcpy(eregs, nwl_dma_engine_registers, j * sizeof(pcilib_register_description_t));
+
+ for (i = 0; i < 2 * PCILIB_MAX_DMA_ENGINES; i++) {
+ pcilib_dma_engine_description_t edesc;
+ char *addr = ctx->base_addr + DMA_OFFSET + i * DMA_ENGINE_PER_SIZE;
- memset(ctx->engines + n_engines, 0, sizeof(pcilib_nwl_engine_description_t));
+ memset(&edesc, 0, sizeof(pcilib_dma_engine_description_t));
- err = dma_nwl_read_engine_config(ctx, ctx->engines + n_engines, addr);
- if (err) continue;
+ err = dma_nwl_read_engine_config(ctx, &edesc, addr);
+ if (err) continue;
+
+ for (j = 0; nwl_dma_engine_registers[j].bits; j++) {
+ int dma_addr_len = (PCILIB_MAX_DMA_ENGINES > 9)?2:1;
+ const char *dma_direction;
+
+ eregs[j].name = nwl_dma_engine_register_names[i * NWL_MAX_DMA_ENGINE_REGISTERS + j];
+ eregs[j].addr = nwl_dma_engine_registers[j].addr + (addr - ctx->base_addr);
- pcilib_set_dma_engine_description(pcilib, n_engines, (pcilib_dma_engine_description_t*)(ctx->engines + n_engines));
- ++n_engines;
+ switch (edesc.direction) {
+ case PCILIB_DMA_FROM_DEVICE:
+ dma_direction = "r";
+ break;
+ case PCILIB_DMA_TO_DEVICE:
+ dma_direction = "w";
+ break;
+ default:
+ dma_direction = "";
+ }
+ sprintf((char*)eregs[j].name, nwl_dma_engine_registers[j].name, dma_addr_len, edesc.addr, dma_direction);
}
- pcilib_set_dma_engine_description(pcilib, n_engines, NULL);
-
- ctx->n_engines = n_engines;
- err = nwl_add_registers(ctx);
+ err = pcilib_add_registers(pcilib, j, eregs);
if (err) {
free(ctx);
- pcilib_error("Failed to add DMA registers");
+ pcilib_error("Error (%i) adding NWL DMA registers for engine %i", err, edesc.addr);
return NULL;
}
+
+ dma = pcilib_add_dma_engine(pcilib, &edesc);
+ if (dma == PCILIB_DMA_ENGINE_INVALID) {
+ free(ctx);
+ pcilib_error("Problem while registering DMA engine");
+ return NULL;
+ }
+
+ ctx->engines[dma].desc = &pcilib->engines[dma];
+ ctx->engines[dma].base_addr = addr;
}
+
return (pcilib_dma_context_t*)ctx;
}
@@ -130,7 +175,7 @@ void dma_nwl_free(pcilib_dma_context_t *vctx) {
nwl_dma_t *ctx = (nwl_dma_t*)vctx;
if (ctx) {
- if (ctx->type == PCILIB_DMA_MODIFICATION_DEFAULT) dma_nwl_stop_loopback(ctx);
+ if (ctx->type == NWL_MODIFICATION_DEFAULT) dma_nwl_stop_loopback(ctx);
dma_nwl_free_irq(ctx);
dma_nwl_stop(vctx, PCILIB_DMA_ENGINE_ALL, PCILIB_DMA_FLAGS_DEFAULT);
diff --git a/dma/nwl.h b/dma/nwl.h
index 21df94c..d4742fd 100644
--- a/dma/nwl.h
+++ b/dma/nwl.h
@@ -4,9 +4,7 @@
#include <stdio.h>
#include "../pcilib.h"
-#define PCILIB_NWL_MODIFICATION_IPECAMERA 0x100
-
-pcilib_dma_context_t *dma_nwl_init(pcilib_t *ctx, pcilib_dma_modification_t type, void *arg);
+pcilib_dma_context_t *dma_nwl_init(pcilib_t *ctx, const char *model, const void *arg);
void dma_nwl_free(pcilib_dma_context_t *vctx);
int dma_nwl_get_status(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dma_engine_status_t *status, size_t n_buffers, pcilib_dma_buffer_status_t *buffers);
@@ -22,10 +20,8 @@ int dma_nwl_write_fragment(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma,
int dma_nwl_stream_read(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, uintptr_t addr, size_t size, pcilib_dma_flags_t flags, pcilib_timeout_t timeout, pcilib_dma_callback_t cb, void *cbattr);
double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dma, uintptr_t addr, size_t size, size_t iterations, pcilib_dma_direction_t direction);
-
-#ifdef _PCILIB_DMA_NWL_C
-pcilib_dma_api_description_t nwl_dma_api = {
- "nwl_dma",
+#ifdef _PCILIB_CONFIG_C
+static const pcilib_dma_api_description_t nwl_dma_api = {
dma_nwl_init,
dma_nwl_free,
dma_nwl_get_status,
@@ -38,9 +34,94 @@ pcilib_dma_api_description_t nwl_dma_api = {
dma_nwl_stream_read,
dma_nwl_benchmark
};
-#else
-extern pcilib_dma_api_description_t nwl_dma_api;
-#endif
+static pcilib_register_bank_description_t nwl_dma_banks[] = {
+ { PCILIB_REGISTER_BANK_DMA, PCILIB_BAR0, 0xA000, PCILIB_REGISTER_PROTOCOL_DEFAULT , 0, 0, PCILIB_LITTLE_ENDIAN, 32, PCILIB_LITTLE_ENDIAN, "0x%lx", "dma", "DMA Registers"},
+ { 0, 0, 0, 0, 0, 0, 0, 0, 0, NULL, NULL, NULL }
+};
+
+static pcilib_register_description_t nwl_dma_registers[] = {
+ {0x4000, 0, 32, 0, 0x00000011, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_control_and_status", ""},
+ {0x4000, 0, 1, 0, 0x00000011, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_enable", ""},
+ {0x4000, 1, 1, 0, 0x00000011, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_active", ""},
+ {0x4000, 2, 1, 0, 0x00000011, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_pending", ""},
+ {0x4000, 3, 1, 0, 0x00000011, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_mode", ""},
+ {0x4000, 4, 1, 0, 0x00000011, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_user_interrupt_enable", ""},
+ {0x4000, 5, 1, 0, 0x00000011, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_user_interrupt_active", ""},
+ {0x4000, 16, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_s2c_interrupt_status", ""},
+ {0x4000, 24, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_c2s_interrupt_status", ""},
+ {0x8000, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_design_version", ""},
+ {0x8000, 0, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_subversion_number", ""},
+ {0x8000, 4, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_version_number", ""},
+ {0x8000, 28, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_targeted_device", ""},
+ {0x8200, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_transmit_utilization", ""},
+ {0x8200, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_transmit_sample_count", ""},
+ {0x8200, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_transmit_dword_count", ""},
+ {0x8204, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_receive_utilization", ""},
+ {0x8004, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_receive_sample_count", ""},
+ {0x8004, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_receive_dword_count", ""},
+ {0x8208, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_mwr", ""},
+ {0x8008, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_mwr_sample_count", ""},
+ {0x8008, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_mwr_dword_count", ""},
+ {0x820C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_cpld", ""},
+ {0x820C, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_cpld_sample_count", ""},
+ {0x820C, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_cpld_dword_count", ""},
+ {0x8210, 0, 12, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_cpld", ""},
+ {0x8214, 0, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_cplh", ""},
+ {0x8218, 0, 12, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_npd", ""},
+ {0x821C, 0, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_nph", ""},
+ {0x8220, 0, 12, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_pd", ""},
+ {0x8224, 0, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_ph", ""},
+ {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
+};
+
+#endif /* _PCILIB_CONFIG_C */
+
+#ifdef _PCILIB_DMA_NWL_C
+ // DMA Engine Registers
+#define NWL_MAX_DMA_ENGINE_REGISTERS 64
+#define NWL_MAX_REGISTER_NAME 128
+static char nwl_dma_engine_register_names[PCILIB_MAX_DMA_ENGINES * NWL_MAX_DMA_ENGINE_REGISTERS][NWL_MAX_REGISTER_NAME];
+static pcilib_register_description_t nwl_dma_engine_registers[] = {
+ {0x0000, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_engine_capabilities", ""},
+ {0x0000, 0, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_present", ""},
+ {0x0000, 1, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_direction", ""},
+ {0x0000, 4, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_type", ""},
+ {0x0000, 8, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_number", ""},
+ {0x0000, 24, 6, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_max_buffer_size", ""},
+ {0x0004, 0, 32, 0, 0x0000C100, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_engine_control", ""},
+ {0x0004, 0, 1, 0, 0x0000C100, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_interrupt_enable", ""},
+ {0x0004, 1, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_interrupt_active", ""},
+ {0x0004, 2, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_descriptor_complete", ""},
+ {0x0004, 3, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_descriptor_alignment_error", ""},
+ {0x0004, 4, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_descriptor_fetch_error", ""},
+ {0x0004, 5, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_sw_abort_error", ""},
+ {0x0004, 8, 1, 0, 0x0000C100, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_enable", ""},
+ {0x0004, 10, 1, 0, 0x0000C100, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_running", ""},
+ {0x0004, 11, 1, 0, 0x0000C100, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_waiting", ""},
+ {0x0004, 14, 1, 0, 0x0000C100, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_reset_request", ""},
+ {0x0004, 15, 1, 0, 0x0000C100, PCILIB_REGISTER_W , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_reset", ""},
+ {0x0008, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_next_descriptor", ""},
+ {0x000C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_sw_descriptor", ""},
+ {0x0010, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_last_descriptor", ""},
+ {0x0014, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_active_time", ""},
+ {0x0018, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_wait_time", ""},
+ {0x001C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_counter", ""},
+ {0x001C, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_sample_count", ""},
+ {0x001C, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_dword_count", ""},
+ {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
+};
+
+ // XRAWDATA registers
+static pcilib_register_description_t nwl_xrawdata_registers[] = {
+ {0x9100, 0, 1, 0, 0x00000000, PCILIB_REGISTER_RW, PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_enable_generator", ""},
+ {0x9104, 0, 16, 0, 0x00000000, PCILIB_REGISTER_RW, PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_packet_length", ""},
+ {0x9108, 0, 2, 0, 0x00000003, PCILIB_REGISTER_RW, PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_control", ""},
+ {0x9108, 0, 1, 0, 0x00000003, PCILIB_REGISTER_RW, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "xrawdata_enable_checker", ""},
+ {0x9108, 1, 1, 0, 0x00000003, PCILIB_REGISTER_RW, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "xrawdata_enable_loopback", ""},
+ {0x910C, 0, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_data_mistmatch", ""},
+ {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
+};
+#endif /* _PCILIB_DMA_NWL_C */
#endif /* _PCILIB_DMA_NWL_H */
diff --git a/dma/nwl_engine.c b/dma/nwl_engine.c
index f541d0b..a437948 100644
--- a/dma/nwl_engine.c
+++ b/dma/nwl_engine.c
@@ -10,46 +10,41 @@
#include "pcilib.h"
#include "error.h"
#include "tools.h"
-#include "nwl_private.h"
+#include "nwl_private.h"
#include "nwl_defines.h"
-
#include "nwl_engine_buffers.h"
-int dma_nwl_read_engine_config(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info, char *base) {
+int dma_nwl_read_engine_config(nwl_dma_t *ctx, pcilib_dma_engine_description_t *info, const char *base) {
uint32_t val;
- info->base_addr = base;
-
nwl_read_register(val, ctx, base, REG_DMA_ENG_CAP);
if ((val & DMA_ENG_PRESENT_MASK) == 0) return PCILIB_ERROR_NOTAVAILABLE;
- info->desc.addr = (val & DMA_ENG_NUMBER) >> DMA_ENG_NUMBER_SHIFT;
- if ((info->desc.addr > PCILIB_MAX_DMA_ENGINES)||(info->desc.addr < 0)) return PCILIB_ERROR_INVALID_DATA;
+ info->addr = (val & DMA_ENG_NUMBER) >> DMA_ENG_NUMBER_SHIFT;
+ if ((info->addr > PCILIB_MAX_DMA_ENGINES)||(info->addr < 0)) return PCILIB_ERROR_INVALID_DATA;
switch (val & DMA_ENG_DIRECTION_MASK) {
case DMA_ENG_C2S:
- info->desc.direction = PCILIB_DMA_FROM_DEVICE;
+ info->direction = PCILIB_DMA_FROM_DEVICE;
break;
default:
- info->desc.direction = PCILIB_DMA_TO_DEVICE;
+ info->direction = PCILIB_DMA_TO_DEVICE;
}
switch (val & DMA_ENG_TYPE_MASK) {
case DMA_ENG_BLOCK:
- info->desc.type = PCILIB_DMA_TYPE_BLOCK;
+ info->type = PCILIB_DMA_TYPE_BLOCK;
break;
case DMA_ENG_PACKET:
- info->desc.type = PCILIB_DMA_TYPE_PACKET;
+ info->type = PCILIB_DMA_TYPE_PACKET;
break;
default:
- info->desc.type = PCILIB_DMA_TYPE_UNKNOWN;
+ info->type = PCILIB_DMA_TYPE_UNKNOWN;
}
- info->desc.addr_bits = (val & DMA_ENG_BD_MAX_BC) >> DMA_ENG_BD_MAX_BC_SHIFT;
-
- info->base_addr = base;
+ info->addr_bits = (val & DMA_ENG_BD_MAX_BC) >> DMA_ENG_BD_MAX_BC_SHIFT;
return 0;
}
@@ -60,22 +55,21 @@ int dma_nwl_start_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
uint32_t ring_pa;
struct timeval start, cur;
- pcilib_nwl_engine_description_t *info = ctx->engines + dma;
+ pcilib_nwl_engine_context_t *ectx = ctx->engines + dma;
char *base = ctx->engines[dma].base_addr;
- if (info->started) return 0;
-
+ if (ectx->started) return 0;
// This will only successed if there are no parallel access to DMA engine
- err = dma_nwl_allocate_engine_buffers(ctx, info);
+ err = dma_nwl_allocate_engine_buffers(ctx, ectx);
if (err) {
- info->started = 1;
+ ectx->started = 1;
dma_nwl_stop_engine(ctx, dma);
return err;
}
- if (info->reused) {
- info->preserve = 1;
+ if (ectx->reused) {
+ ectx->preserve = 1;
dma_nwl_acknowledge_irq((pcilib_dma_context_t*)ctx, PCILIB_DMA_IRQ, dma);
@@ -86,7 +80,7 @@ int dma_nwl_start_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
// Disable IRQs
err = dma_nwl_disable_engine_irq(ctx, dma);
if (err) {
- info->started = 1;
+ ectx->started = 1;
dma_nwl_stop_engine(ctx, dma);
return err;
}
@@ -102,9 +96,9 @@ int dma_nwl_start_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
} while ((val & (DMA_ENG_STATE_MASK|DMA_ENG_USER_RESET))&&(((cur.tv_sec - start.tv_sec)*1000000 + (cur.tv_usec - start.tv_usec)) < PCILIB_REGISTER_TIMEOUT));
if (val & (DMA_ENG_STATE_MASK|DMA_ENG_USER_RESET)) {
- pcilib_error("Timeout during reset of DMA engine %i", info->desc.addr);
+ pcilib_error("Timeout during reset of DMA engine %i", ectx->desc->addr);
- info->started = 1;
+ ectx->started = 1;
dma_nwl_stop_engine(ctx, dma);
return PCILIB_ERROR_TIMEOUT;
}
@@ -119,24 +113,24 @@ int dma_nwl_start_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
} while ((val & DMA_ENG_RESET)&&(((cur.tv_sec - start.tv_sec)*1000000 + (cur.tv_usec - start.tv_usec)) < PCILIB_REGISTER_TIMEOUT));
if (val & DMA_ENG_RESET) {
- pcilib_error("Timeout during reset of DMA engine %i", info->desc.addr);
+ pcilib_error("Timeout during reset of DMA engine %i", ectx->desc->addr);
- info->started = 1;
+ ectx->started = 1;
dma_nwl_stop_engine(ctx, dma);
return PCILIB_ERROR_TIMEOUT;
}
dma_nwl_acknowledge_irq((pcilib_dma_context_t*)ctx, PCILIB_DMA_IRQ, dma);
- ring_pa = pcilib_kmem_get_pa(ctx->pcilib, info->ring);
- nwl_write_register(ring_pa, ctx, info->base_addr, REG_DMA_ENG_NEXT_BD);
- nwl_write_register(ring_pa, ctx, info->base_addr, REG_SW_NEXT_BD);
+ ring_pa = pcilib_kmem_get_pa(ctx->dmactx.pcilib, ectx->ring);
+ nwl_write_register(ring_pa, ctx, ectx->base_addr, REG_DMA_ENG_NEXT_BD);
+ nwl_write_register(ring_pa, ctx, ectx->base_addr, REG_SW_NEXT_BD);
__sync_synchronize();
- nwl_read_register(val, ctx, info->base_addr, REG_DMA_ENG_CTRL_STATUS);
+ nwl_read_register(val, ctx, ectx->base_addr, REG_DMA_ENG_CTRL_STATUS);
val |= (DMA_ENG_ENABLE);
- nwl_write_register(val, ctx, info->base_addr, REG_DMA_ENG_CTRL_STATUS);
+ nwl_write_register(val, ctx, ectx->base_addr, REG_DMA_ENG_CTRL_STATUS);
__sync_synchronize();
@@ -144,19 +138,19 @@ int dma_nwl_start_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
dma_nwl_enable_engine_irq(ctx, dma);
#endif /* NWL_GENERATE_DMA_IRQ */
- if (info->desc.direction == PCILIB_DMA_FROM_DEVICE) {
- ring_pa += (info->ring_size - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- nwl_write_register(ring_pa, ctx, info->base_addr, REG_SW_NEXT_BD);
+ if (ectx->desc->direction == PCILIB_DMA_FROM_DEVICE) {
+ ring_pa += (ectx->ring_size - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ nwl_write_register(ring_pa, ctx, ectx->base_addr, REG_SW_NEXT_BD);
- info->tail = 0;
- info->head = (info->ring_size - 1);
+ ectx->tail = 0;
+ ectx->head = (ectx->ring_size - 1);
} else {
- info->tail = 0;
- info->head = 0;
+ ectx->tail = 0;
+ ectx->head = 0;
}
}
- info->started = 1;
+ ectx->started = 1;
return 0;
}
@@ -170,17 +164,17 @@ int dma_nwl_stop_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
pcilib_kmem_flags_t flags;
- pcilib_nwl_engine_description_t *info = ctx->engines + dma;
+ pcilib_nwl_engine_context_t *ectx = ctx->engines + dma;
char *base = ctx->engines[dma].base_addr;
- if (!info->started) return 0;
+ if (!ectx->started) return 0;
- info->started = 0;
+ ectx->started = 0;
err = dma_nwl_disable_engine_irq(ctx, dma);
if (err) return err;
- if (!info->preserve) {
+ if (!ectx->preserve) {
// Stopping DMA is not enough reset is required
val = DMA_ENG_DISABLE|DMA_ENG_USER_RESET|DMA_ENG_RESET;
nwl_write_register(val, ctx, base, REG_DMA_ENG_CTRL_STATUS);
@@ -191,30 +185,30 @@ int dma_nwl_stop_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma) {
gettimeofday(&cur, NULL);
} while ((val & (DMA_ENG_RUNNING))&&(((cur.tv_sec - start.tv_sec)*1000000 + (cur.tv_usec - start.tv_usec)) < PCILIB_REGISTER_TIMEOUT));
- if (info->ring) {
- ring_pa = pcilib_kmem_get_pa(ctx->pcilib, info->ring);
- nwl_write_register(ring_pa, ctx, info->base_addr, REG_DMA_ENG_NEXT_BD);
- nwl_write_register(ring_pa, ctx, info->base_addr, REG_SW_NEXT_BD);
+ if (ectx->ring) {
+ ring_pa = pcilib_kmem_get_pa(ctx->dmactx.pcilib, ectx->ring);
+ nwl_write_register(ring_pa, ctx, ectx->base_addr, REG_DMA_ENG_NEXT_BD);
+ nwl_write_register(ring_pa, ctx, ectx->base_addr, REG_SW_NEXT_BD);
}
}
dma_nwl_acknowledge_irq((pcilib_dma_context_t*)ctx, PCILIB_DMA_IRQ, dma);
- if (info->preserve) {
+ if (ectx->preserve) {
flags = PCILIB_KMEM_FLAG_REUSE;
} else {
flags = PCILIB_KMEM_FLAG_HARDWARE|PCILIB_KMEM_FLAG_PERSISTENT;
}
// Clean buffers
- if (info->ring) {
- pcilib_free_kernel_memory(ctx->pcilib, info->ring, flags);
- info->ring = NULL;
+ if (ectx->ring) {
+ pcilib_free_kernel_memory(ctx->dmactx.pcilib, ectx->ring, flags);
+ ectx->ring = NULL;
}
- if (info->pages) {
- pcilib_free_kernel_memory(ctx->pcilib, info->pages, flags);
- info->pages = NULL;
+ if (ectx->pages) {
+ pcilib_free_kernel_memory(ctx->dmactx.pcilib, ectx->pages, flags);
+ ectx->pages = NULL;
}
return 0;
@@ -226,28 +220,28 @@ int dma_nwl_write_fragment(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma,
size_t bufnum;
nwl_dma_t *ctx = (nwl_dma_t*)vctx;
- pcilib_nwl_engine_description_t *info = ctx->engines + dma;
+ pcilib_nwl_engine_context_t *ectx = ctx->engines + dma;
err = dma_nwl_start(vctx, dma, PCILIB_DMA_FLAGS_DEFAULT);
if (err) return err;
if (data) {
- for (pos = 0; pos < size; pos += info->page_size) {
- int block_size = min2(size - pos, info->page_size);
+ for (pos = 0; pos < size; pos += ectx->page_size) {
+ int block_size = min2(size - pos, ectx->page_size);
- bufnum = dma_nwl_get_next_buffer(ctx, info, 1, timeout);
+ bufnum = dma_nwl_get_next_buffer(ctx, ectx, 1, timeout);
if (bufnum == PCILIB_DMA_BUFFER_INVALID) {
if (written) *written = pos;
return PCILIB_ERROR_TIMEOUT;
}
- void *buf = pcilib_kmem_get_block_ua(ctx->pcilib, info->pages, bufnum);
+ void *buf = pcilib_kmem_get_block_ua(ctx->dmactx.pcilib, ectx->pages, bufnum);
- pcilib_kmem_sync_block(ctx->pcilib, info->pages, PCILIB_KMEM_SYNC_FROMDEVICE, bufnum);
+ pcilib_kmem_sync_block(ctx->dmactx.pcilib, ectx->pages, PCILIB_KMEM_SYNC_FROMDEVICE, bufnum);
memcpy(buf, data, block_size);
- pcilib_kmem_sync_block(ctx->pcilib, info->pages, PCILIB_KMEM_SYNC_TODEVICE, bufnum);
+ pcilib_kmem_sync_block(ctx->dmactx.pcilib, ectx->pages, PCILIB_KMEM_SYNC_TODEVICE, bufnum);
- err = dma_nwl_push_buffer(ctx, info, block_size, (flags&PCILIB_DMA_FLAG_EOP)&&((pos + block_size) == size), timeout);
+ err = dma_nwl_push_buffer(ctx, ectx, block_size, (flags&PCILIB_DMA_FLAG_EOP)&&((pos + block_size) == size), timeout);
if (err) {
if (written) *written = pos;
return err;
@@ -258,7 +252,7 @@ int dma_nwl_write_fragment(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma,
if (written) *written = size;
if (flags&PCILIB_DMA_FLAG_WAIT) {
- bufnum = dma_nwl_get_next_buffer(ctx, info, PCILIB_NWL_DMA_PAGES - 1, timeout);
+ bufnum = dma_nwl_get_next_buffer(ctx, ectx, PCILIB_NWL_DMA_PAGES - 1, timeout);
if (bufnum == PCILIB_DMA_BUFFER_INVALID) return PCILIB_ERROR_TIMEOUT;
}
@@ -276,7 +270,7 @@ int dma_nwl_stream_read(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, uin
int eop;
- pcilib_nwl_engine_description_t *info = ctx->engines + dma;
+ pcilib_nwl_engine_context_t *ectx = ctx->engines + dma;
err = dma_nwl_start(vctx, dma, PCILIB_DMA_FLAGS_DEFAULT);
if (err) return err;
@@ -288,21 +282,21 @@ int dma_nwl_stream_read(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, uin
// case PCILIB_STREAMING_CHECK: wait = 0; break;
}
- bufnum = dma_nwl_wait_buffer(ctx, info, &bufsize, &eop, wait);
+ bufnum = dma_nwl_wait_buffer(ctx, ectx, &bufsize, &eop, wait);
if (bufnum == PCILIB_DMA_BUFFER_INVALID) {
return (ret&PCILIB_STREAMING_FAIL)?PCILIB_ERROR_TIMEOUT:0;
}
// EOP is not respected in IPE Camera
- if (ctx->dmactx.ignore_eop) eop = 1;
+ if (ctx->ignore_eop) eop = 1;
- pcilib_kmem_sync_block(ctx->pcilib, info->pages, PCILIB_KMEM_SYNC_FROMDEVICE, bufnum);
- void *buf = pcilib_kmem_get_block_ua(ctx->pcilib, info->pages, bufnum);
+ pcilib_kmem_sync_block(ctx->dmactx.pcilib, ectx->pages, PCILIB_KMEM_SYNC_FROMDEVICE, bufnum);
+ void *buf = pcilib_kmem_get_block_ua(ctx->dmactx.pcilib, ectx->pages, bufnum);
ret = cb(cbattr, (eop?PCILIB_DMA_FLAG_EOP:0), bufsize, buf);
if (ret < 0) return -ret;
// DS: Fixme, it looks like we can avoid calling this for the sake of performance
-// pcilib_kmem_sync_block(ctx->pcilib, info->pages, PCILIB_KMEM_SYNC_TODEVICE, bufnum);
- dma_nwl_return_buffer(ctx, info);
+// pcilib_kmem_sync_block(ctx->dmactx.pcilib, ectx->pages, PCILIB_KMEM_SYNC_TODEVICE, bufnum);
+ dma_nwl_return_buffer(ctx, ectx);
res += bufsize;
diff --git a/dma/nwl_engine.h b/dma/nwl_engine.h
index f9f3f60..5f1fa9d 100644
--- a/dma/nwl_engine.h
+++ b/dma/nwl_engine.h
@@ -1,7 +1,7 @@
#ifndef _PCILIB_DMA_NWL_ENGINE_H
#define _PCILIB_DMA_NWL_ENGINE_H
-int dma_nwl_read_engine_config(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info, char *base);
+int dma_nwl_read_engine_config(nwl_dma_t *ctx, pcilib_dma_engine_description_t *info, const char *base);
int dma_nwl_start_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma);
int dma_nwl_stop_engine(nwl_dma_t *ctx, pcilib_dma_engine_t dma);
diff --git a/dma/nwl_engine_buffers.h b/dma/nwl_engine_buffers.h
index c45c3ca..71fb736 100644
--- a/dma/nwl_engine_buffers.h
+++ b/dma/nwl_engine_buffers.h
@@ -2,10 +2,10 @@
#define NWL_RING_SET(data, offset, val) *(uint32_t*)(((char*)(data)) + (offset)) = (val)
#define NWL_RING_UPDATE(data, offset, mask, val) *(uint32_t*)(((char*)(data)) + (offset)) = ((*(uint32_t*)(((char*)(data)) + (offset)))&(mask))|(val)
-static int dma_nwl_compute_read_s2c_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info, unsigned char *ring, uint32_t ring_pa) {
+static int dma_nwl_compute_read_s2c_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx, unsigned char *ring, uint32_t ring_pa) {
uint32_t val;
- char *base = info->base_addr;
+ const char *base = ectx->base_addr;
nwl_read_register(val, ctx, base, REG_SW_NEXT_BD);
if ((val < ring_pa)||((val - ring_pa) % PCILIB_NWL_DMA_DESCRIPTOR_SIZE)) {
@@ -14,9 +14,9 @@ static int dma_nwl_compute_read_s2c_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_d
return PCILIB_ERROR_INVALID_STATE;
}
- info->head = (val - ring_pa) / PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- if (info->head >= PCILIB_NWL_DMA_PAGES) {
- pcilib_warning("Inconsistent S2C DMA Ring buffer is found (REG_SW_NEXT_BD register value (%zu) out of range)", info->head);
+ ectx->head = (val - ring_pa) / PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ if (ectx->head >= PCILIB_NWL_DMA_PAGES) {
+ pcilib_warning("Inconsistent S2C DMA Ring buffer is found (REG_SW_NEXT_BD register value (%zu) out of range)", ectx->head);
return PCILIB_ERROR_INVALID_STATE;
}
@@ -27,23 +27,23 @@ static int dma_nwl_compute_read_s2c_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_d
return PCILIB_ERROR_INVALID_STATE;
}
- info->tail = (val - ring_pa) / PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- if (info->tail >= PCILIB_NWL_DMA_PAGES) {
- pcilib_warning("Inconsistent S2C DMA Ring buffer is found (REG_DMA_ENG_NEXT_BD register value (%zu) out of range)", info->tail);
+ ectx->tail = (val - ring_pa) / PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ if (ectx->tail >= PCILIB_NWL_DMA_PAGES) {
+ pcilib_warning("Inconsistent S2C DMA Ring buffer is found (REG_DMA_ENG_NEXT_BD register value (%zu) out of range)", ectx->tail);
return PCILIB_ERROR_INVALID_STATE;
}
#ifdef DEBUG_NWL
- printf("S2C: %lu %lu\n", info->tail, info->head);
+ printf("S2C: %lu %lu\n", ectx->tail, ectx->head);
#endif /* DEBUG_NWL */
return 0;
}
-static int dma_nwl_compute_read_c2s_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info, unsigned char *ring, uint32_t ring_pa) {
+static int dma_nwl_compute_read_c2s_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx, unsigned char *ring, uint32_t ring_pa) {
uint32_t val;
- char *base = info->base_addr;
+ const char *base = ectx->base_addr;
nwl_read_register(val, ctx, base, REG_SW_NEXT_BD);
if ((val < ring_pa)||((val - ring_pa) % PCILIB_NWL_DMA_DESCRIPTOR_SIZE)) {
@@ -52,24 +52,24 @@ static int dma_nwl_compute_read_c2s_pointers(nwl_dma_t *ctx, pcilib_nwl_engine_d
return PCILIB_ERROR_INVALID_STATE;
}
- info->head = (val - ring_pa) / PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- if (info->head >= PCILIB_NWL_DMA_PAGES) {
- pcilib_warning("Inconsistent C2S DMA Ring buffer is found (REG_SW_NEXT_BD register value (%zu) out of range)", info->head);
+ ectx->head = (val - ring_pa) / PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ if (ectx->head >= PCILIB_NWL_DMA_PAGES) {
+ pcilib_warning("Inconsistent C2S DMA Ring buffer is found (REG_SW_NEXT_BD register value (%zu) out of range)", ectx->head);
return PCILIB_ERROR_INVALID_STATE;
}
- info->tail = info->head + 1;
- if (info->tail == PCILIB_NWL_DMA_PAGES) info->tail = 0;
+ ectx->tail = ectx->head + 1;
+ if (ectx->tail == PCILIB_NWL_DMA_PAGES) ectx->tail = 0;
#ifdef DEBUG_NWL
- printf("C2S: %lu %lu\n", info->tail, info->head);
+ printf("C2S: %lu %lu\n", ectx->tail, ectx->head);
#endif /* DEBUG_NWL */
return 0;
}
-static int dma_nwl_allocate_engine_buffers(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info) {
+static int dma_nwl_allocate_engine_buffers(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx) {
int err = 0;
int i;
@@ -82,39 +82,39 @@ static int dma_nwl_allocate_engine_buffers(nwl_dma_t *ctx, pcilib_nwl_engine_des
pcilib_kmem_flags_t flags;
pcilib_kmem_type_t type;
- char *base = info->base_addr;
+ char *base = ectx->base_addr;
- if (info->pages) return 0;
+ if (ectx->pages) return 0;
// Or bidirectional specified by 0x0|addr, or read 0x0|addr and write 0x80|addr
- type = (info->desc.direction == PCILIB_DMA_TO_DEVICE)?PCILIB_KMEM_TYPE_DMA_S2C_PAGE:PCILIB_KMEM_TYPE_DMA_C2S_PAGE;
- sub_use = info->desc.addr|((info->desc.direction == PCILIB_DMA_TO_DEVICE)?0x80:0x00);
- flags = PCILIB_KMEM_FLAG_REUSE|PCILIB_KMEM_FLAG_EXCLUSIVE|PCILIB_KMEM_FLAG_HARDWARE|(info->preserve?PCILIB_KMEM_FLAG_PERSISTENT:0);
+ type = (ectx->desc->direction == PCILIB_DMA_TO_DEVICE)?PCILIB_KMEM_TYPE_DMA_S2C_PAGE:PCILIB_KMEM_TYPE_DMA_C2S_PAGE;
+ sub_use = ectx->desc->addr|((ectx->desc->direction == PCILIB_DMA_TO_DEVICE)?0x80:0x00);
+ flags = PCILIB_KMEM_FLAG_REUSE|PCILIB_KMEM_FLAG_EXCLUSIVE|PCILIB_KMEM_FLAG_HARDWARE|(ectx->preserve?PCILIB_KMEM_FLAG_PERSISTENT:0);
- pcilib_kmem_handle_t *ring = pcilib_alloc_kernel_memory(ctx->pcilib, PCILIB_KMEM_TYPE_CONSISTENT, 1, PCILIB_NWL_DMA_PAGES * PCILIB_NWL_DMA_DESCRIPTOR_SIZE, PCILIB_NWL_ALIGNMENT, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_RING, sub_use), flags);
- pcilib_kmem_handle_t *pages = pcilib_alloc_kernel_memory(ctx->pcilib, type, PCILIB_NWL_DMA_PAGES, 0, 0, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_PAGES, sub_use), flags);
+ pcilib_kmem_handle_t *ring = pcilib_alloc_kernel_memory(ctx->dmactx.pcilib, PCILIB_KMEM_TYPE_CONSISTENT, 1, PCILIB_NWL_DMA_PAGES * PCILIB_NWL_DMA_DESCRIPTOR_SIZE, PCILIB_NWL_ALIGNMENT, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_RING, sub_use), flags);
+ pcilib_kmem_handle_t *pages = pcilib_alloc_kernel_memory(ctx->dmactx.pcilib, type, PCILIB_NWL_DMA_PAGES, 0, 0, PCILIB_KMEM_USE(PCILIB_KMEM_USE_DMA_PAGES, sub_use), flags);
if (!ring||!pages) {
- if (pages) pcilib_free_kernel_memory(ctx->pcilib, pages, 0);
- if (ring) pcilib_free_kernel_memory(ctx->pcilib, ring, 0);
+ if (pages) pcilib_free_kernel_memory(ctx->dmactx.pcilib, pages, 0);
+ if (ring) pcilib_free_kernel_memory(ctx->dmactx.pcilib, ring, 0);
return PCILIB_ERROR_MEMORY;
}
- reuse_ring = pcilib_kmem_is_reused(ctx->pcilib, ring);
- reuse_pages = pcilib_kmem_is_reused(ctx->pcilib, pages);
+ reuse_ring = pcilib_kmem_is_reused(ctx->dmactx.pcilib, ring);
+ reuse_pages = pcilib_kmem_is_reused(ctx->dmactx.pcilib, pages);
// I guess idea here was that we not need to check all that stuff during the second iteration
// which is basicaly true (shall we expect any driver-triggered changes or parallel accesses?)
// but still we need to set preserve flag (and that if we enforcing preservation --start-dma).
// Probably having checks anyway is not harming...
-// if (!info->preserve) {
+// if (!ectx->preserve) {
if (reuse_ring == reuse_pages) {
if (reuse_ring & PCILIB_KMEM_REUSE_PARTIAL) pcilib_warning("Inconsistent DMA buffers are found (only part of required buffers is available), reinitializing...");
else if (reuse_ring & PCILIB_KMEM_REUSE_REUSED) {
if ((reuse_ring & PCILIB_KMEM_REUSE_PERSISTENT) == 0) pcilib_warning("Lost DMA buffers are found (non-persistent mode), reinitializing...");
else if ((reuse_ring & PCILIB_KMEM_REUSE_HARDWARE) == 0) pcilib_warning("Lost DMA buffers are found (missing HW reference), reinitializing...");
else {
- nwl_read_register(val, ctx, info->base_addr, REG_DMA_ENG_CTRL_STATUS);
+ nwl_read_register(val, ctx, ectx->base_addr, REG_DMA_ENG_CTRL_STATUS);
if ((val&DMA_ENG_RUNNING) == 0) pcilib_warning("Lost DMA buffers are found (DMA engine is stopped), reinitializing...");
else preserve = 1;
@@ -124,27 +124,27 @@ static int dma_nwl_allocate_engine_buffers(nwl_dma_t *ctx, pcilib_nwl_engine_des
// }
- unsigned char *data = (unsigned char*)pcilib_kmem_get_ua(ctx->pcilib, ring);
- uint32_t ring_pa = pcilib_kmem_get_pa(ctx->pcilib, ring);
+ unsigned char *data = (unsigned char*)pcilib_kmem_get_ua(ctx->dmactx.pcilib, ring);
+ uint32_t ring_pa = pcilib_kmem_get_pa(ctx->dmactx.pcilib, ring);
if (preserve) {
- if (info->desc.direction == PCILIB_DMA_FROM_DEVICE) err = dma_nwl_compute_read_c2s_pointers(ctx, info, data, ring_pa);
- else err = dma_nwl_compute_read_s2c_pointers(ctx, info, data, ring_pa);
+ if (ectx->desc->direction == PCILIB_DMA_FROM_DEVICE) err = dma_nwl_compute_read_c2s_pointers(ctx, ectx, data, ring_pa);
+ else err = dma_nwl_compute_read_s2c_pointers(ctx, ectx, data, ring_pa);
if (err) preserve = 0;
}
if (preserve) {
- info->reused = 1;
- buf_sz = pcilib_kmem_get_block_size(ctx->pcilib, pages, 0);
+ ectx->reused = 1;
+ buf_sz = pcilib_kmem_get_block_size(ctx->dmactx.pcilib, pages, 0);
} else {
- info->reused = 0;
+ ectx->reused = 0;
memset(data, 0, PCILIB_NWL_DMA_PAGES * PCILIB_NWL_DMA_DESCRIPTOR_SIZE);
for (i = 0; i < PCILIB_NWL_DMA_PAGES; i++, data += PCILIB_NWL_DMA_DESCRIPTOR_SIZE) {
- buf_pa = pcilib_kmem_get_block_pa(ctx->pcilib, pages, i);
- buf_sz = pcilib_kmem_get_block_size(ctx->pcilib, pages, i);
+ buf_pa = pcilib_kmem_get_block_pa(ctx->dmactx.pcilib, pages, i);
+ buf_sz = pcilib_kmem_get_block_size(ctx->dmactx.pcilib, pages, i);
NWL_RING_SET(data, DMA_BD_NDESC_OFFSET, ring_pa + ((i + 1) % PCILIB_NWL_DMA_PAGES) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE);
NWL_RING_SET(data, DMA_BD_BUFAL_OFFSET, buf_pa&0xFFFFFFFF);
@@ -160,25 +160,25 @@ static int dma_nwl_allocate_engine_buffers(nwl_dma_t *ctx, pcilib_nwl_engine_des
nwl_write_register(val, ctx, base, REG_DMA_ENG_NEXT_BD);
nwl_write_register(val, ctx, base, REG_SW_NEXT_BD);
- info->head = 0;
- info->tail = 0;
+ ectx->head = 0;
+ ectx->tail = 0;
}
- info->ring = ring;
- info->pages = pages;
- info->page_size = buf_sz;
- info->ring_size = PCILIB_NWL_DMA_PAGES;
+ ectx->ring = ring;
+ ectx->pages = pages;
+ ectx->page_size = buf_sz;
+ ectx->ring_size = PCILIB_NWL_DMA_PAGES;
return 0;
}
-static size_t dma_nwl_clean_buffers(nwl_dma_t * ctx, pcilib_nwl_engine_description_t *info) {
+static size_t dma_nwl_clean_buffers(nwl_dma_t * ctx, pcilib_nwl_engine_context_t *ectx) {
size_t res = 0;
uint32_t status;
- unsigned char *ring = pcilib_kmem_get_ua(ctx->pcilib, info->ring);
- ring += info->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ unsigned char *ring = pcilib_kmem_get_ua(ctx->dmactx.pcilib, ectx->ring);
+ ring += ectx->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
next_buffer:
status = NWL_RING_GET(ring, DMA_BD_BUFL_STATUS_OFFSET)&DMA_BD_STATUS_MASK;
@@ -195,17 +195,17 @@ next_buffer:
}
if (status & DMA_BD_COMP_MASK) {
- info->tail++;
- if (info->tail == info->ring_size) {
- ring -= (info->tail - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- info->tail = 0;
+ ectx->tail++;
+ if (ectx->tail == ectx->ring_size) {
+ ring -= (ectx->tail - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ ectx->tail = 0;
} else {
ring += PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
}
res++;
- if (info->tail != info->head) goto next_buffer;
+ if (ectx->tail != ectx->head) goto next_buffer;
}
// printf("====> Cleaned: %i\n", res);
@@ -213,18 +213,18 @@ next_buffer:
}
-static size_t dma_nwl_get_next_buffer(nwl_dma_t * ctx, pcilib_nwl_engine_description_t *info, size_t n_buffers, pcilib_timeout_t timeout) {
+static size_t dma_nwl_get_next_buffer(nwl_dma_t * ctx, pcilib_nwl_engine_context_t *ectx, size_t n_buffers, pcilib_timeout_t timeout) {
struct timeval start, cur;
size_t res, n = 0;
size_t head;
- for (head = info->head; (((head + 1)%info->ring_size) != info->tail)&&(n < n_buffers); head++, n++);
- if (n == n_buffers) return info->head;
+ for (head = ectx->head; (((head + 1)%ectx->ring_size) != ectx->tail)&&(n < n_buffers); head++, n++);
+ if (n == n_buffers) return ectx->head;
gettimeofday(&start, NULL);
- res = dma_nwl_clean_buffers(ctx, info);
+ res = dma_nwl_clean_buffers(ctx, ectx);
if (res == (size_t)-1) return PCILIB_DMA_BUFFER_INVALID;
else n += res;
@@ -237,7 +237,7 @@ static size_t dma_nwl_get_next_buffer(nwl_dma_t * ctx, pcilib_nwl_engine_descrip
usleep (10);
- res = dma_nwl_clean_buffers(ctx, info);
+ res = dma_nwl_clean_buffers(ctx, ectx);
if (res == (size_t)-1) return PCILIB_DMA_BUFFER_INVALID;
else if (res > 0) {
gettimeofday(&start, NULL);
@@ -247,48 +247,48 @@ static size_t dma_nwl_get_next_buffer(nwl_dma_t * ctx, pcilib_nwl_engine_descrip
if (n < n_buffers) return PCILIB_DMA_BUFFER_INVALID;
- return info->head;
+ return ectx->head;
}
-static int dma_nwl_push_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info, size_t size, int eop, pcilib_timeout_t timeout) {
+static int dma_nwl_push_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx, size_t size, int eop, pcilib_timeout_t timeout) {
int flags = 0;
uint32_t val;
- unsigned char *ring = pcilib_kmem_get_ua(ctx->pcilib, info->ring);
- uint32_t ring_pa = pcilib_kmem_get_pa(ctx->pcilib, info->ring);
+ unsigned char *ring = pcilib_kmem_get_ua(ctx->dmactx.pcilib, ectx->ring);
+ uint32_t ring_pa = pcilib_kmem_get_pa(ctx->dmactx.pcilib, ectx->ring);
- ring += info->head * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ ring += ectx->head * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- if (!info->writting) {
+ if (!ectx->writting) {
flags |= DMA_BD_SOP_MASK;
- info->writting = 1;
+ ectx->writting = 1;
}
if (eop) {
flags |= DMA_BD_EOP_MASK;
- info->writting = 0;
+ ectx->writting = 0;
}
NWL_RING_SET(ring, DMA_BD_BUFL_CTRL_OFFSET, size|flags);
NWL_RING_SET(ring, DMA_BD_BUFL_STATUS_OFFSET, size);
- info->head++;
- if (info->head == info->ring_size) info->head = 0;
+ ectx->head++;
+ if (ectx->head == ectx->ring_size) ectx->head = 0;
- val = ring_pa + info->head * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- nwl_write_register(val, ctx, info->base_addr, REG_SW_NEXT_BD);
+ val = ring_pa + ectx->head * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ nwl_write_register(val, ctx, ectx->base_addr, REG_SW_NEXT_BD);
return 0;
}
-static size_t dma_nwl_wait_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info, size_t *size, int *eop, pcilib_timeout_t timeout) {
+static size_t dma_nwl_wait_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx, size_t *size, int *eop, pcilib_timeout_t timeout) {
struct timeval start, cur;
uint32_t status_size, status;
- unsigned char *ring = pcilib_kmem_get_ua(ctx->pcilib, info->ring);
+ unsigned char *ring = pcilib_kmem_get_ua(ctx->dmactx.pcilib, ectx->ring);
- ring += info->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ ring += ectx->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
gettimeofday(&start, NULL);
@@ -309,13 +309,13 @@ static size_t dma_nwl_wait_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_description_
/*
if (mrd) {
- if ((info->tail + 1) == info->ring_size) ring -= info->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ if ((ectx->tail + 1) == ectx->ring_size) ring -= ectx->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
else ring += PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
*mrd = NWL_RING_GET(ring, DMA_BD_BUFL_STATUS_OFFSET)&DMA_BD_COMP_MASK;
}
*/
- return info->tail;
+ return ectx->tail;
}
usleep(10);
@@ -327,25 +327,25 @@ static size_t dma_nwl_wait_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_description_
/*
// This function is not used now, but we may need it in the future
-static int dma_nwl_is_overflown(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info) {
+static int dma_nwl_is_overflown(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx) {
uint32_t status;
- unsigned char *ring = pcilib_kmem_get_ua(ctx->pcilib, info->ring);
- if (info->tail > 0) ring += (info->tail - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- else ring += (info->ring_size - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ unsigned char *ring = pcilib_kmem_get_ua(ctx->dmactx.pcilib, ectx->ring);
+ if (ectx->tail > 0) ring += (ectx->tail - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ else ring += (ectx->ring_size - 1) * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
status = NWL_RING_GET(ring, DMA_BD_BUFL_STATUS_OFFSET);
return status&DMA_BD_COMP_MASK?1:0;
}
*/
-static int dma_nwl_return_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_description_t *info) {
+static int dma_nwl_return_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_context_t *ectx) {
uint32_t val;
- unsigned char *ring = pcilib_kmem_get_ua(ctx->pcilib, info->ring);
- uint32_t ring_pa = pcilib_kmem_get_pa(ctx->pcilib, info->ring);
- size_t bufsz = pcilib_kmem_get_block_size(ctx->pcilib, info->pages, info->tail);
+ unsigned char *ring = pcilib_kmem_get_ua(ctx->dmactx.pcilib, ectx->ring);
+ uint32_t ring_pa = pcilib_kmem_get_pa(ctx->dmactx.pcilib, ectx->ring);
+ size_t bufsz = pcilib_kmem_get_block_size(ctx->dmactx.pcilib, ectx->pages, ectx->tail);
- ring += info->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ ring += ectx->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
#ifdef NWL_GENERATE_DMA_IRQ
NWL_RING_SET(ring, DMA_BD_BUFL_CTRL_OFFSET, bufsz | DMA_BD_INT_ERROR_MASK | DMA_BD_INT_COMP_MASK);
@@ -355,11 +355,11 @@ static int dma_nwl_return_buffer(nwl_dma_t *ctx, pcilib_nwl_engine_description_t
NWL_RING_SET(ring, DMA_BD_BUFL_STATUS_OFFSET, 0);
- val = ring_pa + info->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
- nwl_write_register(val, ctx, info->base_addr, REG_SW_NEXT_BD);
+ val = ring_pa + ectx->tail * PCILIB_NWL_DMA_DESCRIPTOR_SIZE;
+ nwl_write_register(val, ctx, ectx->base_addr, REG_SW_NEXT_BD);
- info->tail++;
- if (info->tail == info->ring_size) info->tail = 0;
+ ectx->tail++;
+ if (ectx->tail == ectx->ring_size) ectx->tail = 0;
return 0;
}
@@ -368,34 +368,34 @@ int dma_nwl_get_status(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcil
size_t i;
uint32_t bstatus;
nwl_dma_t *ctx = (nwl_dma_t*)vctx;
- pcilib_nwl_engine_description_t *info = ctx->engines + dma;
- unsigned char *ring = (unsigned char*)pcilib_kmem_get_ua(ctx->pcilib, info->ring);
+ pcilib_nwl_engine_context_t *ectx = ctx->engines + dma;
+ unsigned char *ring = (unsigned char*)pcilib_kmem_get_ua(ctx->dmactx.pcilib, ectx->ring);
if (!status) return -1;
- status->started = info->started;
- status->ring_size = info->ring_size;
- status->buffer_size = info->page_size;
- status->ring_tail = info->tail;
+ status->started = ectx->started;
+ status->ring_size = ectx->ring_size;
+ status->buffer_size = ectx->page_size;
+ status->ring_tail = ectx->tail;
- if (info->desc.direction == PCILIB_DMA_FROM_DEVICE) {
+ if (ectx->desc->direction == PCILIB_DMA_FROM_DEVICE) {
size_t pos = 0;
- for (i = 0; i < info->ring_size; i++) {
+ for (i = 0; i < ectx->ring_size; i++) {
pos = status->ring_tail + i;
- if (pos >= info->ring_size) pos -= info->ring_size;
+ if (pos >= ectx->ring_size) pos -= ectx->ring_size;
bstatus = NWL_RING_GET(ring + pos * PCILIB_NWL_DMA_DESCRIPTOR_SIZE, DMA_BD_BUFL_STATUS_OFFSET);
if ((bstatus&(DMA_BD_ERROR_MASK|DMA_BD_COMP_MASK)) == 0) break;
}
status->ring_head = pos;
} else {
- status->ring_head = info->head;
+ status->ring_head = ectx->head;
}
if (buffers) {
- for (i = 0; (i < info->ring_size)&&(i < n_buffers); i++) {
+ for (i = 0; (i < ectx->ring_size)&&(i < n_buffers); i++) {
bstatus = NWL_RING_GET(ring, DMA_BD_BUFL_STATUS_OFFSET);
buffers[i].error = bstatus & (DMA_BD_ERROR_MASK/*|DMA_BD_SHORT_MASK*/);
diff --git a/dma/nwl_irq.c b/dma/nwl_irq.c
index e71c76a..cbc087b 100644
--- a/dma/nwl_irq.c
+++ b/dma/nwl_irq.c
@@ -49,7 +49,7 @@ int dma_nwl_enable_irq(pcilib_dma_context_t *vctx, pcilib_irq_type_t type, pcili
val &= ~(DMA_INT_ENABLE|DMA_USER_INT_ENABLE);
nwl_write_register(val, ctx, ctx->base_addr, REG_DMA_CTRL_STATUS);
- pcilib_clear_irq(ctx->pcilib, NWL_DMA_IRQ_SOURCE);
+ pcilib_clear_irq(ctx->dmactx.pcilib, NWL_DMA_IRQ_SOURCE);
if (type & PCILIB_DMA_IRQ) val |= DMA_INT_ENABLE;
if (type & PCILIB_EVENT_IRQ) val |= DMA_USER_INT_ENABLE;
@@ -104,15 +104,15 @@ int dma_nwl_acknowledge_irq(pcilib_dma_context_t *vctx, pcilib_irq_type_t irq_ty
uint32_t val;
nwl_dma_t *ctx = (nwl_dma_t*)vctx;
- pcilib_nwl_engine_description_t *info = ctx->engines + irq_source;
+ pcilib_nwl_engine_context_t *ectx = ctx->engines + irq_source;
if (irq_type != PCILIB_DMA_IRQ) return PCILIB_ERROR_NOTSUPPORTED;
- if (irq_source >= ctx->n_engines) return PCILIB_ERROR_NOTAVAILABLE;
+ if (irq_source >= ctx->dmactx.pcilib->num_engines) return PCILIB_ERROR_NOTAVAILABLE;
- nwl_read_register(val, ctx, info->base_addr, REG_DMA_ENG_CTRL_STATUS);
+ nwl_read_register(val, ctx, ectx->base_addr, REG_DMA_ENG_CTRL_STATUS);
if (val & DMA_ENG_INT_ACTIVE_MASK) {
val |= DMA_ENG_ALLINT_MASK;
- nwl_write_register(val, ctx, info->base_addr, REG_DMA_ENG_CTRL_STATUS);
+ nwl_write_register(val, ctx, ectx->base_addr, REG_DMA_ENG_CTRL_STATUS);
}
return 0;
diff --git a/dma/nwl_irq.h b/dma/nwl_irq.h
index 811b632..b49946b 100644
--- a/dma/nwl_irq.h
+++ b/dma/nwl_irq.h
@@ -1,5 +1,5 @@
-#ifndef _PCILIB_NWL_IRQ_H
-#define _PCILIB_NWL_IRQ_H
+#ifndef _PCILIB_DMA_NWL_IRQ_H
+#define _PCILIB_DMA_NWL_IRQ_H
int dma_nwl_init_irq(nwl_dma_t *ctx, uint32_t val);
int dma_nwl_free_irq(nwl_dma_t *ctx);
@@ -7,4 +7,4 @@ int dma_nwl_free_irq(nwl_dma_t *ctx);
int dma_nwl_enable_engine_irq(nwl_dma_t *ctx, pcilib_dma_engine_t dma);
int dma_nwl_disable_engine_irq(nwl_dma_t *ctx, pcilib_dma_engine_t dma);
-#endif /* _PCILIB_NWL_IRQ_H */
+#endif /* _PCILIB_DMA_NWL_IRQ_H */
diff --git a/dma/nwl_loopback.c b/dma/nwl_loopback.c
index 381a462..1a0cd93 100644
--- a/dma/nwl_loopback.c
+++ b/dma/nwl_loopback.c
@@ -25,7 +25,7 @@ int dma_nwl_start_loopback(nwl_dma_t *ctx, pcilib_dma_direction_t direction, si
val = packet_size;
nwl_write_register(val, ctx, ctx->base_addr, PKT_SIZE_ADDRESS);
- if (ctx->type == PCILIB_DMA_MODIFICATION_DEFAULT) {
+ if (ctx->type == NWL_MODIFICATION_DEFAULT) {
switch (direction) {
case PCILIB_DMA_BIDIRECTIONAL:
val = LOOPBACK;
@@ -54,7 +54,7 @@ int dma_nwl_stop_loopback(nwl_dma_t *ctx) {
engine initialized in previous run, and benchmark is only actual usage.
Otherwise, we should detect current loopback status during initialization */
- if (ctx->type == PCILIB_DMA_MODIFICATION_DEFAULT) {
+ if (ctx->type == NWL_MODIFICATION_DEFAULT) {
nwl_write_register(val, ctx, ctx->base_addr, TX_CONFIG_ADDRESS);
nwl_write_register(val, ctx, ctx->base_addr, RX_CONFIG_ADDRESS);
}
@@ -77,25 +77,25 @@ double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
nwl_dma_t *ctx = (nwl_dma_t*)vctx;
- pcilib_dma_engine_t readid = pcilib_find_dma_by_addr(ctx->pcilib, PCILIB_DMA_FROM_DEVICE, dma);
- pcilib_dma_engine_t writeid = pcilib_find_dma_by_addr(ctx->pcilib, PCILIB_DMA_TO_DEVICE, dma);
+ pcilib_dma_engine_t readid = pcilib_find_dma_by_addr(ctx->dmactx.pcilib, PCILIB_DMA_FROM_DEVICE, dma);
+ pcilib_dma_engine_t writeid = pcilib_find_dma_by_addr(ctx->dmactx.pcilib, PCILIB_DMA_TO_DEVICE, dma);
if (size%sizeof(uint32_t)) size = 1 + size / sizeof(uint32_t);
else size /= sizeof(uint32_t);
// Not supported
- if (ctx->type == PCILIB_DMA_MODIFICATION_DEFAULT) {
+ if (ctx->type == NWL_MODIFICATION_DEFAULT) {
if (direction == PCILIB_DMA_TO_DEVICE) return -1.;
}
-// else if ((direction == PCILIB_DMA_FROM_DEVICE)&&(ctx->type != PCILIB_DMA_MODIFICATION_DEFAULT)) return -1.;
+// else if ((direction == PCILIB_DMA_FROM_DEVICE)&&(ctx->type != NWL_MODIFICATION_DEFAULT)) return -1.;
// Stop Generators and drain old data
- if (ctx->type == PCILIB_DMA_MODIFICATION_DEFAULT) dma_nwl_stop_loopback(ctx);
+ if (ctx->type == NWL_MODIFICATION_DEFAULT) dma_nwl_stop_loopback(ctx);
// dma_nwl_stop_engine(ctx, readid); // DS: replace with something better
__sync_synchronize();
- err = pcilib_skip_dma(ctx->pcilib, readid);
+ err = pcilib_skip_dma(ctx->dmactx.pcilib, readid);
if (err) {
pcilib_error("Can't start benchmark, devices continuously writes unexpected data using DMA engine");
return -1;
@@ -125,31 +125,31 @@ double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
return -1;
}
- if (ctx->type == PCILIB_NWL_MODIFICATION_IPECAMERA) {
- pcilib_write_register(ctx->pcilib, NULL, "control", 0x1e5);
+ if (ctx->type == NWL_MODIFICATION_IPECAMERA) {
+ pcilib_write_register(ctx->dmactx.pcilib, NULL, "control", 0x1e5);
usleep(100000);
- pcilib_write_register(ctx->pcilib, NULL, "control", 0x1e1);
+ pcilib_write_register(ctx->dmactx.pcilib, NULL, "control", 0x1e1);
// This way causes more problems with garbage
- //pcilib_write_register(ctx->pcilib, NULL, "control", 0x3e1);
+ //pcilib_write_register(ctx->dmactx.pcilib, NULL, "control", 0x3e1);
}
// Benchmark
for (iter = 0; iter < iterations; iter++) {
memset(cmp, 0x13 + iter, size * sizeof(uint32_t));
- if (ctx->type == PCILIB_NWL_MODIFICATION_IPECAMERA) {
- pcilib_write_register(ctx->pcilib, NULL, "control", 0x1e1);
+ if (ctx->type == NWL_MODIFICATION_IPECAMERA) {
+ pcilib_write_register(ctx->dmactx.pcilib, NULL, "control", 0x1e1);
}
- if ((direction&PCILIB_DMA_TO_DEVICE)||(ctx->type != PCILIB_DMA_MODIFICATION_DEFAULT)) {
+ if ((direction&PCILIB_DMA_TO_DEVICE)||(ctx->type != NWL_MODIFICATION_DEFAULT)) {
memcpy(buf, cmp, size * sizeof(uint32_t));
if (direction&PCILIB_DMA_TO_DEVICE) {
gettimeofday(&start, NULL);
}
- err = pcilib_write_dma(ctx->pcilib, writeid, addr, size * sizeof(uint32_t), buf, &bytes);
+ err = pcilib_write_dma(ctx->dmactx.pcilib, writeid, addr, size * sizeof(uint32_t), buf, &bytes);
if ((err)||(bytes != size * sizeof(uint32_t))) {
error = "Write failed";
break;
@@ -165,8 +165,8 @@ double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
}
}
- if (ctx->type == PCILIB_NWL_MODIFICATION_IPECAMERA) {
- pcilib_write_register(ctx->pcilib, NULL, "control", 0x3e1);
+ if (ctx->type == NWL_MODIFICATION_IPECAMERA) {
+ pcilib_write_register(ctx->dmactx.pcilib, NULL, "control", 0x3e1);
}
memset(buf, 0, size * sizeof(uint32_t));
@@ -180,7 +180,7 @@ double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
retry:
#endif
- err = pcilib_read_dma(ctx->pcilib, readid, addr, packet_size * sizeof(uint32_t), buf + (bytes>>2), &rbytes);
+ err = pcilib_read_dma(ctx->dmactx.pcilib, readid, addr, packet_size * sizeof(uint32_t), buf + (bytes>>2), &rbytes);
if ((err)||(rbytes%sizeof(uint32_t))) {
break;
}
@@ -227,8 +227,8 @@ double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
#endif
}
- if (ctx->type == PCILIB_NWL_MODIFICATION_IPECAMERA) {
- pcilib_write_register(ctx->pcilib, NULL, "control", 0x1e1);
+ if (ctx->type == NWL_MODIFICATION_IPECAMERA) {
+ pcilib_write_register(ctx->dmactx.pcilib, NULL, "control", 0x1e1);
}
if (error) {
@@ -245,7 +245,7 @@ double dma_nwl_benchmark(pcilib_dma_context_t *vctx, pcilib_dma_engine_addr_t dm
__sync_synchronize();
if (direction == PCILIB_DMA_FROM_DEVICE) {
- pcilib_skip_dma(ctx->pcilib, readid);
+ pcilib_skip_dma(ctx->dmactx.pcilib, readid);
}
free(cmp);
diff --git a/dma/nwl_loopback.h b/dma/nwl_loopback.h
index 63c8446..d0b53cf 100644
--- a/dma/nwl_loopback.h
+++ b/dma/nwl_loopback.h
@@ -1,7 +1,7 @@
-#ifndef _PCILIB_NWL_LOOPBACK_H
-#define _PCILIB_NWL_LOOPBACK_H
+#ifndef _PCILIB_DMA_NWL_LOOPBACK_H
+#define _PCILIB_DMA_NWL_LOOPBACK_H
int dma_nwl_start_loopback(nwl_dma_t *ctx, pcilib_dma_direction_t direction, size_t packet_size);
int dma_nwl_stop_loopback(nwl_dma_t *ctx);
-#endif /* _PCILIB_NWL_LOOPBACK_H */
+#endif /* _PCILIB_DMA_NWL_LOOPBACK_H */
diff --git a/dma/nwl_private.h b/dma/nwl_private.h
index 756e6ca..934fa04 100644
--- a/dma/nwl_private.h
+++ b/dma/nwl_private.h
@@ -2,7 +2,7 @@
#define _PCILIB_DMA_NWL_PRIVATE_H
typedef struct nwl_dma_s nwl_dma_t;
-typedef struct pcilib_nwl_engine_description_s pcilib_nwl_engine_description_t;
+typedef struct pcilib_nwl_engine_context_s pcilib_nwl_engine_context_t;
#define NWL_DMA_IRQ_SOURCE 0
@@ -20,17 +20,17 @@ typedef struct pcilib_nwl_engine_description_s pcilib_nwl_engine_description_t;
#include "nwl.h"
#include "nwl_irq.h"
-#include "nwl_register.h"
#include "nwl_engine.h"
#include "nwl_loopback.h"
#define nwl_read_register(var, ctx, base, reg) pcilib_datacpy(&var, base + reg, 4, 1, ctx->dma_bank->raw_endianess)
#define nwl_write_register(var, ctx, base, reg) pcilib_datacpy(base + reg, &var, 4, 1, ctx->dma_bank->raw_endianess)
-struct pcilib_nwl_engine_description_s {
- pcilib_dma_engine_description_t desc;
+
+struct pcilib_nwl_engine_context_s {
+ const pcilib_dma_engine_description_t *desc;
char *base_addr;
-
+
size_t ring_size, page_size;
size_t head, tail;
pcilib_kmem_handle_t *ring;
@@ -42,15 +42,18 @@ struct pcilib_nwl_engine_description_s {
int preserve; /**< indicates that DMA should not be stopped during clean-up */
};
+typedef enum {
+ NWL_MODIFICATION_DEFAULT,
+ NWL_MODIFICATION_IPECAMERA
+} nwl_modification_t;
struct nwl_dma_s {
- struct pcilib_dma_context_s dmactx;
-
- pcilib_t *pcilib;
-
- pcilib_dma_modification_t type;
-
- pcilib_register_bank_description_t *dma_bank;
+ pcilib_dma_context_t dmactx;
+
+ nwl_modification_t type;
+ int ignore_eop; /**< always set end-of-packet */
+
+ const pcilib_register_bank_description_t *dma_bank;
char *base_addr;
pcilib_irq_type_t irq_enabled; /**< indicates that IRQs are enabled */
@@ -59,9 +62,10 @@ struct nwl_dma_s {
int irq_started; /**< indicates that IRQ subsystem is initialized (detecting which types should be preserverd) */
int loopback_started; /**< indicates that benchmarking subsystem is initialized */
- pcilib_dma_engine_t n_engines;
- pcilib_nwl_engine_description_t engines[PCILIB_MAX_DMA_ENGINES + 1];
+// pcilib_dma_engine_t n_engines;
+ pcilib_nwl_engine_context_t engines[PCILIB_MAX_DMA_ENGINES + 1];
};
+int nwl_add_registers(nwl_dma_t *ctx);
#endif /* _PCILIB_DMA_NWL_PRIVATE_H */
diff --git a/dma/nwl_register.c b/dma/nwl_register.c
deleted file mode 100644
index 6a3771a..0000000
--- a/dma/nwl_register.c
+++ /dev/null
@@ -1,77 +0,0 @@
-#define _PCILIB_NWL_REGISTER_C
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
-#include <sys/time.h>
-
-#include "pcilib.h"
-
-#include "pci.h"
-#include "error.h"
-#include "tools.h"
-
-#include "nwl_private.h"
-#include "nwl_register.h"
-
-int nwl_add_registers(nwl_dma_t *ctx) {
- int err;
- size_t n, i, j;
- int length;
- const char *names[NWL_MAX_DMA_ENGINE_REGISTERS];
- uintptr_t addr[NWL_MAX_DMA_ENGINE_REGISTERS];
-
- // We don't want DMA registers
- if (pcilib_find_bank_by_addr(ctx->pcilib, PCILIB_REGISTER_BANK_DMA) == PCILIB_REGISTER_BANK_INVALID) return 0;
-
- err = pcilib_add_registers(ctx->pcilib, 0, nwl_dma_registers);
- if (err) return err;
-
- if (ctx->type == PCILIB_DMA_MODIFICATION_DEFAULT) {
- err = pcilib_add_registers(ctx->pcilib, 0, nwl_xrawdata_registers);
- if (err) return err;
- }
-
-
- for (n = 0; nwl_dma_engine_registers[n].bits; n++) {
- names[n] = nwl_dma_engine_registers[n].name;
- addr[n] = nwl_dma_engine_registers[n].addr;
- }
-
- if (ctx->n_engines > 9) length = 2;
- else length = 1;
-
-
- for (i = 0; i < ctx->n_engines; i++) {
- for (j = 0; nwl_dma_engine_registers[j].bits; j++) {
- const char *direction;
- nwl_dma_engine_registers[j].name = nwl_dma_engine_register_names[i * NWL_MAX_DMA_ENGINE_REGISTERS + j];
- nwl_dma_engine_registers[j].addr = addr[j] + (ctx->engines[i].base_addr - ctx->base_addr);
-// printf("%lx %lx\n", (ctx->engines[i].base_addr - ctx->base_addr), nwl_dma_engine_registers[j].addr);
-
- switch (ctx->engines[i].desc.direction) {
- case PCILIB_DMA_FROM_DEVICE:
- direction = "r";
- break;
- case PCILIB_DMA_TO_DEVICE:
- direction = "w";
- break;
- default:
- direction = "";
- }
-
- sprintf((char*)nwl_dma_engine_registers[j].name, names[j], length, ctx->engines[i].desc.addr, direction);
- }
-
- err = pcilib_add_registers(ctx->pcilib, n, nwl_dma_engine_registers);
- if (err) return err;
- }
-
- for (n = 0; nwl_dma_engine_registers[n].bits; n++) {
- nwl_dma_engine_registers[n].name = names[n];
- nwl_dma_engine_registers[n].addr = addr[n];
- }
-
- return 0;
-}
diff --git a/dma/nwl_register.h b/dma/nwl_register.h
deleted file mode 100644
index a71942b..0000000
--- a/dma/nwl_register.h
+++ /dev/null
@@ -1,97 +0,0 @@
-#ifndef _PCILIB_NWL_REGISTERS_H
-#define _PCILIB_NWL_REGISTERS_H
-
-#ifdef _PCILIB_NWL_REGISTER_C
- // DMA
-static pcilib_register_description_t nwl_dma_registers[] = {
- {0x4000, 0, 32, 0, 0x00000011, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_control_and_status", ""},
- {0x4000, 0, 1, 0, 0x00000011, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_enable", ""},
- {0x4000, 1, 1, 0, 0x00000011, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_active", ""},
- {0x4000, 2, 1, 0, 0x00000011, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_pending", ""},
- {0x4000, 3, 1, 0, 0x00000011, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_interrupt_mode", ""},
- {0x4000, 4, 1, 0, 0x00000011, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_user_interrupt_enable", ""},
- {0x4000, 5, 1, 0, 0x00000011, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_user_interrupt_active", ""},
- {0x4000, 16, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_s2c_interrupt_status", ""},
- {0x4000, 24, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_c2s_interrupt_status", ""},
- {0x8000, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_design_version", ""},
- {0x8000, 0, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_subversion_number", ""},
- {0x8000, 4, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_version_number", ""},
- {0x8000, 28, 4, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_targeted_device", ""},
- {0x8200, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_transmit_utilization", ""},
- {0x8200, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_transmit_sample_count", ""},
- {0x8200, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_transmit_dword_count", ""},
- {0x8204, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_receive_utilization", ""},
- {0x8004, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_receive_sample_count", ""},
- {0x8004, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_receive_dword_count", ""},
- {0x8208, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_mwr", ""},
- {0x8008, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_mwr_sample_count", ""},
- {0x8008, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_mwr_dword_count", ""},
- {0x820C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_cpld", ""},
- {0x820C, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_cpld_sample_count", ""},
- {0x820C, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma_cpld_dword_count", ""},
- {0x8210, 0, 12, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_cpld", ""},
- {0x8214, 0, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_cplh", ""},
- {0x8218, 0, 12, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_npd", ""},
- {0x821C, 0, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_nph", ""},
- {0x8220, 0, 12, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_pd", ""},
- {0x8224, 0, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma_init_fc_ph", ""},
- {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
-};
-
- // DMA Engine Registers
-#define NWL_MAX_DMA_ENGINE_REGISTERS 64
-#define NWL_MAX_REGISTER_NAME 128
-static char nwl_dma_engine_register_names[PCILIB_MAX_DMA_ENGINES * NWL_MAX_DMA_ENGINE_REGISTERS][NWL_MAX_REGISTER_NAME];
-static pcilib_register_description_t nwl_dma_engine_registers[] = {
- {0x0000, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_engine_capabilities", ""},
- {0x0000, 0, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_present", ""},
- {0x0000, 1, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_direction", ""},
- {0x0000, 4, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_type", ""},
- {0x0000, 8, 8, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_number", ""},
- {0x0000, 24, 6, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_max_buffer_size", ""},
- {0x0004, 0, 32, 0, 0x0000C100, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_engine_control", ""},
- {0x0004, 0, 1, 0, 0x0000C100, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_interrupt_enable", ""},
- {0x0004, 1, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_interrupt_active", ""},
- {0x0004, 2, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_descriptor_complete", ""},
- {0x0004, 3, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_descriptor_alignment_error", ""},
- {0x0004, 4, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_descriptor_fetch_error", ""},
- {0x0004, 5, 1, 0, 0x0000C100, PCILIB_REGISTER_RW1C, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_sw_abort_error", ""},
- {0x0004, 8, 1, 0, 0x0000C100, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_enable", ""},
- {0x0004, 10, 1, 0, 0x0000C100, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_running", ""},
- {0x0004, 11, 1, 0, 0x0000C100, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_waiting", ""},
- {0x0004, 14, 1, 0, 0x0000C100, PCILIB_REGISTER_RW , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_reset_request", ""},
- {0x0004, 15, 1, 0, 0x0000C100, PCILIB_REGISTER_W , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_reset", ""},
- {0x0008, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_next_descriptor", ""},
- {0x000C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_RW , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_sw_descriptor", ""},
- {0x0010, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_last_descriptor", ""},
- {0x0014, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_active_time", ""},
- {0x0018, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_wait_time", ""},
- {0x001C, 0, 32, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_counter", ""},
- {0x001C, 0, 2, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_sample_count", ""},
- {0x001C, 2, 30, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "dma%0*u%s_dword_count", ""},
- {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
-};
-
-/*
- // XAUI registers
-static pcilib_register_description_t nwl_xaui_registers[] = {
- {0, 0, 0, 0, 0, 0, 0, NULL, NULL}
-};
-*/
-
- // XRAWDATA registers
-static pcilib_register_description_t nwl_xrawdata_registers[] = {
- {0x9100, 0, 1, 0, 0x00000000, PCILIB_REGISTER_RW, PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_enable_generator", ""},
- {0x9104, 0, 16, 0, 0x00000000, PCILIB_REGISTER_RW, PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_packet_length", ""},
- {0x9108, 0, 2, 0, 0x00000003, PCILIB_REGISTER_RW, PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_control", ""},
- {0x9108, 0, 1, 0, 0x00000003, PCILIB_REGISTER_RW, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "xrawdata_enable_checker", ""},
- {0x9108, 1, 1, 0, 0x00000003, PCILIB_REGISTER_RW, PCILIB_REGISTER_BITS, PCILIB_REGISTER_BANK_DMA, "xrawdata_enable_loopback", ""},
- {0x910C, 0, 1, 0, 0x00000000, PCILIB_REGISTER_R , PCILIB_REGISTER_STANDARD, PCILIB_REGISTER_BANK_DMA, "xrawdata_data_mistmatch", ""},
- {0, 0, 0, 0, 0x00000000, 0, 0, 0, NULL, NULL}
-};
-
-#endif /* _PCILIB_NWL_REGISTERS_C */
-
-int nwl_add_registers(nwl_dma_t *ctx);
-
-#endif /* _PCILIB_NWL_REGISTERS_H */