summaryrefslogtreecommitdiffstats
path: root/pcilib
diff options
context:
space:
mode:
Diffstat (limited to 'pcilib')
-rw-r--r--pcilib/bar.c13
-rw-r--r--pcilib/datacpy.c2
-rw-r--r--pcilib/fifo.c4
-rw-r--r--pcilib/memcpy.c16
-rw-r--r--pcilib/memcpy.h3
-rw-r--r--pcilib/pcilib.h10
6 files changed, 33 insertions, 15 deletions
diff --git a/pcilib/bar.c b/pcilib/bar.c
index 6d6cd6d..85c0e12 100644
--- a/pcilib/bar.c
+++ b/pcilib/bar.c
@@ -119,6 +119,7 @@ void *pcilib_map_bar(pcilib_t *ctx, pcilib_bar_t bar) {
return NULL;
}
+ ctx->bar_space[bar] = res;
return res;
}
@@ -323,26 +324,26 @@ const pcilib_bar_info_t *pcilib_get_bar_info(pcilib_t *ctx, pcilib_bar_t bar) {
return NULL;
}
-int pcilib_read(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, size_t size, void *buf) {
+int pcilib_read(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, uint8_t access, size_t n, void *buf) {
void *data;
- pcilib_detect_address(ctx, &bar, &addr, size);
+ pcilib_detect_address(ctx, &bar, &addr, access * n);
data = pcilib_map_bar(ctx, bar);
- pcilib_memcpy(buf, data + addr, size);
+ pcilib_memcpy(buf, data + addr, access, n);
pcilib_unmap_bar(ctx, bar, data);
return 0;
}
-int pcilib_write(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, size_t size, void *buf) {
+int pcilib_write(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, uint8_t access, size_t n, void *buf) {
void *data;
- pcilib_detect_address(ctx, &bar, &addr, size);
+ pcilib_detect_address(ctx, &bar, &addr, access * n);
data = pcilib_map_bar(ctx, bar);
- pcilib_memcpy(data + addr, buf, size);
+ pcilib_memcpy(data + addr, buf, access, n);
pcilib_unmap_bar(ctx, bar, data);
diff --git a/pcilib/datacpy.c b/pcilib/datacpy.c
index 15dfbe9..27bff11 100644
--- a/pcilib/datacpy.c
+++ b/pcilib/datacpy.c
@@ -81,7 +81,7 @@ void *pcilib_datacpy(void * dst, void const * src, uint8_t size, size_t n, pcili
size_t pos = 0;
pcilib_datacpy_routine_t routine;
- assert((size)&&(size < 64));
+ assert((size)&&(size <= 8));
while (size >>= 1) ++pos;
routine = pcilib_datacpy_routines[pos];
diff --git a/pcilib/fifo.c b/pcilib/fifo.c
index 7ed87b8..2ae4303 100644
--- a/pcilib/fifo.c
+++ b/pcilib/fifo.c
@@ -31,7 +31,7 @@ int pcilib_read_fifo(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, uint8_t fi
data = pcilib_map_bar(ctx, bar);
for (i = 0; i < n; i++) {
- pcilib_memcpy(buf + i * fifo_size, data + addr, fifo_size);
+ pcilib_memcpy(buf + i * fifo_size, data + addr, fifo_size, 1);
}
pcilib_unmap_bar(ctx, bar, data);
@@ -47,7 +47,7 @@ int pcilib_write_fifo(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, uint8_t f
data = pcilib_map_bar(ctx, bar);
for (i = 0; i < n; i++) {
- pcilib_memcpy(data + addr, buf + i * fifo_size, fifo_size);
+ pcilib_memcpy(data + addr, buf + i * fifo_size, fifo_size, 1);
}
pcilib_unmap_bar(ctx, bar, data);
diff --git a/pcilib/memcpy.c b/pcilib/memcpy.c
index 149d1fd..dd55037 100644
--- a/pcilib/memcpy.c
+++ b/pcilib/memcpy.c
@@ -64,3 +64,19 @@ void *pcilib_memcpy64(void * dst, void const * src, size_t len) {
return (dst);
}
+typedef void* (*pcilib_memcpy_routine_t)(void * dst, void const *src, size_t bytes);
+static pcilib_memcpy_routine_t pcilib_memcpy_routines[4] = {
+ pcilib_memcpy8, NULL, pcilib_memcpy32, pcilib_memcpy64
+};
+
+void *pcilib_memcpy(void * dst, void const * src, uint8_t access, size_t n) {
+ size_t pos = 0, size = n * access;
+ pcilib_memcpy_routine_t routine;
+
+ assert((access)&&(access <= 8));
+
+ while (access >>= 1) ++pos;
+ routine = pcilib_memcpy_routines[pos];
+
+ return routine(dst, src, size);
+}
diff --git a/pcilib/memcpy.h b/pcilib/memcpy.h
index 3ac2115..dbfae36 100644
--- a/pcilib/memcpy.h
+++ b/pcilib/memcpy.h
@@ -5,8 +5,6 @@
#include <stdint.h>
-#define pcilib_memcpy pcilib_memcpy32
-
#ifdef __cplusplus
extern "C" {
#endif
@@ -14,6 +12,7 @@ extern "C" {
void *pcilib_memcpy8(void * dst, void const * src, size_t len);
void *pcilib_memcpy32(void * dst, void const * src, size_t len);
void *pcilib_memcpy64(void * dst, void const * src, size_t len);
+void *pcilib_memcpy(void * dst, void const * src, uint8_t access, size_t n);
#ifdef __cplusplus
}
diff --git a/pcilib/pcilib.h b/pcilib/pcilib.h
index cfe3e96..3e7cf2b 100644
--- a/pcilib/pcilib.h
+++ b/pcilib/pcilib.h
@@ -327,22 +327,24 @@ char *pcilib_resolve_bar_address(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr
* @param[in,out] ctx - pcilib context
* @param[in] bar - the BAR to read, use PCILIB_BAR_DETECT to detect bar by the specified physical address
* @param[in] addr - absolute physical address to read or the offset in the specified bar
- * @param[in] size - number of bytes to read
+ * @param[in] access - word size (access width in bytes)
+ * @param[in] n - number of words to read
* @param[out] buf - the read data will be placed in this buffer
* @return - error code or 0 on success
*/
-int pcilib_read(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, size_t size, void *buf);
+int pcilib_read(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, uint8_t access, size_t n, void *buf);
/**
* Performs PIO write to the PCI BAR. The BAR will be automatically mapped and unmapped if necessary.
* @param[in,out] ctx - pcilib context
* @param[in] bar - the BAR to write, use PCILIB_BAR_DETECT to detect bar by the specified physical address
* @param[in] addr - absolute physical address to write or the offset in the specified bar
- * @param[in] size - number of bytes to write
+ * @param[in] access - word size (access width in bytes)
+ * @param[in] n - number of words to write
* @param[out] buf - the pointer to the data to be written
* @return - error code or 0 on success
*/
-int pcilib_write(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, size_t size, void *buf);
+int pcilib_write(pcilib_t *ctx, pcilib_bar_t bar, uintptr_t addr, uint8_t access, size_t n, void *buf);
/**
* Performs PIO read from the PCI BAR. The specified address is treated as FIFO and will be read