Ver código fonte

Dynamicly set TLP(Payload) size in IPEDMA

Suren A. Chilingaryan 9 anos atrás
pai
commit
e202b682db
2 arquivos alterados com 28 adições e 11 exclusões
  1. 19 5
      dma/ipe.c
  2. 9 6
      dma/ipe_private.h

+ 19 - 5
dma/ipe.c

@@ -97,6 +97,10 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
 
     ipe_dma_t *ctx = (ipe_dma_t*)vctx;
 
+#ifndef IPEDMA_TLP_SIZE
+    const pcilib_pcie_link_info_t *link_info;
+#endif /* ! IPEDMA_TLP_SIZE */
+
     int preserve = 0;
     pcilib_kmem_flags_t kflags;
     pcilib_kmem_reuse_state_t reuse_desc, reuse_pages;
@@ -105,9 +109,9 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
     volatile uint32_t *last_written_addr_ptr;
 
     pcilib_register_value_t value;
-    
+
+    int tlp_size;
     uint32_t address64;
-    
 
     if (dma == PCILIB_DMA_ENGINE_INVALID) return 0;
     else if (dma > 1) return PCILIB_ERROR_INVALID_BANK;
@@ -196,9 +200,19 @@ int dma_ipe_start(pcilib_dma_context_t *vctx, pcilib_dma_engine_t dma, pcilib_dm
 	    // Enable 64 bit addressing and configure TLP and PACKET sizes (40 bit mode can be used with big pre-allocated buffers later)
 	if (ctx->mode64) address64 = 0x8000 | (0<<24);
 	else address64 = 0;
-	
-        WR(IPEDMA_REG_TLP_SIZE,  address64 | IPEDMA_TLP_SIZE);
-        WR(IPEDMA_REG_TLP_COUNT, IPEDMA_PAGE_SIZE / (4 * IPEDMA_TLP_SIZE * IPEDMA_CORES));
+
+#ifdef IPEDMA_TLP_SIZE	
+	tlp_size = IPEDMA_TLP_SIZE;
+#else /* IPEDMA_TLP_SIZE */
+	link_info = pcilib_get_pcie_link_info(vctx->pcilib);
+	if (link_info) {
+	    tlp_size = 1<<link_info->max_payload;
+	    if (tlp_size > IPEDMA_MAX_TLP_SIZE)
+		tlp_size = IPEDMA_MAX_TLP_SIZE;
+	} else tlp_size = 128;
+#endif /* IPEDMA_TLP_SIZE */
+        WR(IPEDMA_REG_TLP_SIZE,  address64 | (tlp_size>>2));
+        WR(IPEDMA_REG_TLP_COUNT, IPEDMA_PAGE_SIZE / (tlp_size * IPEDMA_CORES));
 
 	    // Setting progress register threshold
 	WR(IPEDMA_REG_UPDATE_THRESHOLD, IPEDMA_DMA_PROGRESS_THRESHOLD);

+ 9 - 6
dma/ipe_private.h

@@ -5,22 +5,25 @@
 
 #define IPEDMA_64BIT_MODE		1		/**< 64-bit mode addressing is required to support PCIe gen3 */
 #define IPEDMA_CORES			1
-#define IPEDMA_TLP_SIZE			32
+#define IPEDMA_MAX_TLP_SIZE		256		/**< Defines maximum TLP in bytes supported by device */
+//#define IPEDMA_TLP_SIZE		128		/**< If set, enforces the specified TLP size */
+
 #define IPEDMA_PAGE_SIZE		4096
 #define IPEDMA_DMA_PAGES		32		/**< number of DMA pages in the ring buffer to allocate */
 #define IPEDMA_DMA_PROGRESS_THRESHOLD	1		/**< how many pages the DMA engine should fill before reporting progress */
 #define IPEDMA_DESCRIPTOR_SIZE		128
 #define IPEDMA_DESCRIPTOR_ALIGNMENT	64
 
-#define IPEDMA_BUG_LAST_READ				/**< We should forbid writting the second last available DMA buffer (the last is forbidden by design) */
-#define IPEDMA_RESET_DELAY		100000		/**< Sleep between accessing DMA control and reset registers */
-#define IPEDMA_ADD_PAGE_DELAY		1000		/**< Delay between submitting successive DMA pages into IPEDMA_REG_PAGE_ADDR register */
-#define IPEDMA_NODATA_SLEEP		10		/**< To keep CPU free */
 
 //#define IPEDMA_BUG_DMARD				/**< No register read during DMA transfer */
+//#define IPEDMA_BUG_LAST_READ				/**< We should forbid writting the second last available DMA buffer (the last is forbidden by design) */
 //#define IPEDMA_DETECT_PACKETS				/**< Using empty_deceted flag */
 #define  IPEDMA_SUPPORT_EMPTY_DETECTED			/**< Avoid waiting for data when empty_detected flag is set in hardware */
-#define IPEDMA_DMA_TIMEOUT 100000			/**< us, overrides PCILIB_DMA_TIMEOUT (actual hardware timeout is 50ms according to Lorenzo) */
+
+#define IPEDMA_DMA_TIMEOUT 		100000		/**< us, overrides PCILIB_DMA_TIMEOUT (actual hardware timeout is 50ms according to Lorenzo) */
+#define IPEDMA_RESET_DELAY		100000		/**< Sleep between accessing DMA control and reset registers */
+#define IPEDMA_ADD_PAGE_DELAY		1000		/**< Delay between submitting successive DMA pages into IPEDMA_REG_PAGE_ADDR register */
+#define IPEDMA_NODATA_SLEEP		10		/**< To keep CPU free */
 
 #define IPEDMA_REG_RESET		0x00
 #define IPEDMA_REG_CONTROL		0x04