2、arm端共享内存(0xc200-0000)初始化: /* heap for malloc list node */ IHeap_Handle heap_node = (IHeap_Handle)SharedRegion_getHeap(SYS_CFG_SR_ID_LIST_HEAP); /* heap for malloc buffer for upp data */ IHeap_Handle heap_data = (IHeap_Handle)SharedRegion_getHeap(SYS_CFG_SR_ID_UPP_HEAP); /* create data nodes */ DataNode *nodes[SYS_CFG_LIST_NODES]; int i; for (i = 0; i < SYS_CFG_LIST_NODES; i++) { DataNode *node = (DataNode *)Memory_alloc(heap_node, sizeof(DataNode), 0, NULL); UInt32* data = (UInt32 *)Memory_alloc(heap_data, SR_BUFFER_SIZE, 0, NULL); node->SR_buffer = SharedRegion_getSRPtr(data, SYS_CFG_SR_ID_UPP_HEAP); node->size = SR_BUFFER_SIZE; node->buffer_pitch = BUFFER_PITCH; node->buffer_height = BUFFER_HEIGHT; nodes[i] = node; } 3、dsp接收程序: static bool server_upp_data_transfer(Server *server) { if(server->ad_started == false) return true; while (ListMP_empty(server->list_free)) /* wait */ Task_sleep(10000); DataNode *node = (DataNode *)ListMP_getTail(server->list_free); /* get free node */ int *data = (int *)SharedRegion_getPtr(node->SR_buffer); server->transposeParA.WindowAddress = (unsigned int *)data; /* set taget */ server->transposeParA.LineCount = node->buffer_height; server->transposeParA.ByteCount = node->buffer_pitch; server->transposeParA.LineOffsetAddress = node->buffer_pitch; upp_error_count = 0; upp_dmai_int_cut = 0; /* fill in data */ uPPDMATransfer(SOC_UPP_0_REGS, uPP_DMA_CHI, &server->transposeParA); /* wait */ while (upp_dmai_int_cut < 1 && upp_error_count == 0); if (upp_error_count != 0) { LOG_ERROR("data mismatch in buffers"); LOG_ERROR("upp_error_count=%d",upp_error_count); } /* make data node in busy list */ ListMP_putHead(server->list_busy, (ListMP_Elem *)node); Cache_inv(node,sizeof(DataNode),Cache_Type_L2,true); Cache_inv(data,SR_BUFFER_SIZE,Cache_Type_L2,true); Cache_wait(); da[pdd]=(unsigned int)data; db[pdd]=node->SR_buffer; dd[pdd]=*(data+2); dd1[pdd]=*(data+3); pdd++; return true; } 4、dma中断程序(dsp) void uPPIsr(void) { unsigned int intr_dmai_status, intr_dmaq_status; // 取?? DMA ?卸?状态 intr_dmai_status = uPPIntStatus(SOC_UPP_0_REGS, uPP_DMA_CHI); intr_dmaq_status = uPPIntStatus(SOC_UPP_0_REGS, uPP_DMA_CHQ); while(intr_dmai_status != 0 || intr_dmaq_status != 0) { if (intr_dmai_status & uPP_INT_EOL) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHI, uPP_INT_EOL); } if (intr_dmai_status & uPP_INT_EOW) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHI, uPP_INT_EOW); upp_dmai_int_cut++; } if (intr_dmai_status & uPP_INT_ERR) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHI, uPP_INT_ERR); upp_error_count++; } if (intr_dmai_status & uPP_INT_UOR) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHI, uPP_INT_UOR); upp_error_count++; } if (intr_dmai_status & uPP_INT_DPE) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHI, uPP_INT_DPE); upp_error_count++; } if (intr_dmaq_status & uPP_INT_EOL) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHQ, uPP_INT_EOL); } if (intr_dmaq_status & uPP_INT_EOW) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHQ, uPP_INT_EOW); upp_dmaq_int_cut++; } if (intr_dmaq_status & uPP_INT_ERR) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHQ, uPP_INT_ERR); upp_error_count++; } if (intr_dmaq_status & uPP_INT_UOR) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHQ, uPP_INT_UOR); upp_error_count++; } if (intr_dmaq_status & uPP_INT_DPE) { uPPIntClear(SOC_UPP_0_REGS, uPP_DMA_CHQ, uPP_INT_DPE); upp_error_count++; } // uPP ?卸辖??????录?????为同一?卸?源 // ?卸??欠?全?????楸???????? intr_dmai_status = uPPIntStatus(SOC_UPP_0_REGS, uPP_DMA_CHI); intr_dmaq_status = uPPIntStatus(SOC_UPP_0_REGS, uPP_DMA_CHQ); } // 通知 CPU uPP ?卸洗????????员??????录????圆??? uPPEndOfInt(SOC_UPP_0_REGS); }