最近在xilinx論壇上看到以下的讨論:
XDMA 異常狀态(busy) 如何恢複?
使用zynq7035 xdma gen2, x8,mem模式x ,正常運作時沒有問題。
c2h模式下,mem 接口是由 stream 的資料轉換而來。
一旦 windows 驅動側開啟的c2h.read ,FPGA當中的stream 沒有産生資料,讀取就會卡住,在這個過程中軟體關閉,xdma 的邏輯就會陷入異常,一直處在busy狀态。
無論是重裝驅動還是 重新開機軟體都不能正常啟動,必須重新開機電腦。才能恢複?
有沒有什麼方式能夠在xdma 進入busy狀态後 強行恢複?比如說控制寄存器,或者對驅動進行軟體操作?
論壇中始終沒有答案,恰巧自己在用的時候也出現了上述的問題,我的運作環境如下:
硬體:NVIDIA TX2I
軟體:官方的XDMA驅動,github上的201901版本
通過檢視輸出的資訊,調試發現是由于在XDMA引擎stop之後沒有設定相應的結束狀态導緻的,更改如下:
static int xdma_engine_stop(struct xdma_engine *engine)
{
u32 w;
if (!engine) {
pr_err("dma engine NULL\n");
return -EINVAL;
}
dbg_tfr("%s(engine=%p)\n", __func__, engine);
w = 0;
w |= (u32)XDMA_CTRL_IE_DESC_ALIGN_MISMATCH;
w |= (u32)XDMA_CTRL_IE_MAGIC_STOPPED;
w |= (u32)XDMA_CTRL_IE_READ_ERROR;
w |= (u32)XDMA_CTRL_IE_DESC_ERROR;
if (poll_mode) {
w |= (u32)XDMA_CTRL_POLL_MODE_WB;
} else {
w |= (u32)XDMA_CTRL_IE_DESC_STOPPED;
w |= (u32)XDMA_CTRL_IE_DESC_COMPLETED;
}
dbg_tfr("Stopping SG DMA %s engine; writing 0x%08x to 0x%p.\n",
engine->name, w, (u32 *)&engine->regs->control);
write_register(w, &engine->regs->control,
(unsigned long)(&engine->regs->control) -
(unsigned long)(&engine->regs));
engine->running = 0; //++++++++++++++++++++++++++++++
dbg_tfr("%s(%s) done\n", __func__, engine->name);
return 0;
}