// +FHDR------------------------------------------------------------ // Copyright (c) 2022 SmartLogic. // ALL RIGHTS RESERVED // ----------------------------------------------------------------- // Filename : arm_csu.c // Author : xinxin.li // Created On : 2022-11-23 // Last Modified : // ----------------------------------------------------------------- // Description: // // // -FHDR------------------------------------------------------------ #include "ucp_csu.h" #include "arm_csu.h" #include #include #include #include #include #include #include #include #include #include #include "ucp_utility.h" #include "ucp_printf.h" #include "drv_init.h" uint8_t* virMemAddr = NULL; int arm_csu_init() { if (-1 == g_drv_mem_fd) { // printf("open dev mem. \r\n"); g_drv_mem_fd = open("/dev/mem", O_RDWR|O_SYNC); if (0 > g_drv_mem_fd) { UCP_PRINT_ERROR("open /dev/mem error\n"); return -1; } } // printf("start mmap. \r\n"); virMemAddr = (uint8_t*)mmap(NULL, CSU_DEV_MAP_LEN, PROT_READ|PROT_WRITE, MAP_SHARED, g_drv_mem_fd, AP_CSU_BASE); if ((uint8_t*)(-1) == virMemAddr) { UCP_PRINT_ERROR("mmap error!!"); return -1; } // printf("csu init. \r\n"); int i; for (i = 0; i < 16; i++) { *((volatile uint32_t*)(virMemAddr+AP_CSU_DMAYNUMXNUM0) + (i<<3)) = ((4<<16)|1024); *((volatile uint32_t*)(virMemAddr+AP_CSU_DMAYSTEPL0) + (i<<3)) = 1024; *((volatile uint32_t*)(virMemAddr+AP_CSU_DMAYSTEPH0) + (i<<3)) = 0; *((volatile uint32_t*)(virMemAddr+AP_CSU_DMAZSTEPL0) + (i<<3)) = 4096; *((volatile uint32_t*)(virMemAddr+AP_CSU_DMAZSTEPH0) + (i<<3)) = 0; } *((volatile uint32_t*)(virMemAddr+AP_CSU_EM_BS_SMSEL_PREDATANUM)) = (0x2A<<16) | (0x0<<14) | (0x5<<5) | 0x9; // (0x3F<<16); *((volatile uint32_t*)(virMemAddr+AP_CSU_EM_BS_SMSEL_PREDATANUM)) = (0x2A<<16) | (0x1<<14) | (0x5<<5) | 0x9; *((volatile uint32_t*)(virMemAddr+AP_CSU_EM_BS_SMSEL_PREDATANUM)) = (0x2A<<16) | (0x2<<14) | (0x5<<5) | 0x9; *((volatile uint32_t*)(virMemAddr+AP_CSU_EM_BS_SMSEL_PREDATANUM)) = (0x2A<<16) | (0x3<<14) | (0x5<<5) | 0x9; *((volatile uint32_t*)(virMemAddr+AP_CSU_FINDDMATAG)) = 0x60; *((volatile uint32_t*)(virMemAddr+AP_CSU_TAGMASK0)) = 0xFFFFFFFF; *((volatile uint32_t*)(virMemAddr+AP_CSU_TAGMASK1)) = 0xFFFFFFFF; *((volatile uint32_t*)(virMemAddr+AP_CSU_TAGMASK2)) = 0xFFFFFFFF; *((volatile uint32_t*)(virMemAddr+AP_CSU_TAGMASK3)) = 0xFFFFFFFF; return 0; } int get_arm_csu_status(uint8_t tag) { if (31 < tag) { UCP_PRINT_ERROR("input para error! tag = %d. \r\n", tag); return -1; } uint32_t status = VIR_ADDR_VAL(virMemAddr, AP_CSU_DMASTATUS); return (status&(1<1) //tag 4 5 6 7 1(2->3) //tag 8 9 10 11 2(4->5) //tag 12 13 14 15 3(6->7) //tag 16 17 18 19 4(8->9) //tag 20 21 22 23 5(10->11) //tag 24 25 26 27 6(12->13) //tag 28 29 30 31 7(14->15) // get unused register group according to tag number int get_free_reg_group(uint8_t tag) { if (31 < tag) { return -1; } uint32_t dmaStatus = VIR_ADDR_VAL(virMemAddr, AP_CSU_DMASTATUS); uint8_t fifoNum = tag % 4; uint8_t regGroup = tag / 4; if (0 == (dmaStatus & (0xF<>16) & 0xFF; int ret = regGroup | (fifoNum<<8) | (tag<<16); return ret; } } } } } int arm_csu_dma_1D_transfer(uint64_t addrSrc, uint64_t addrDst, uint32_t dataLen) { uint8_t regGroup = 0; uint8_t fifoNum = 0; uint8_t tag = 0; uint32_t temp = get_free_channel(); // printf("get free channle: 0x%x. \r\n", temp); regGroup = temp & 0xFF; fifoNum = (temp>>8) & 0xFF; tag = (temp>>16)&0xFF; uint8_t offset = regGroup << 6; // src reg VIR_ADDR_VAL(virMemAddr, AP_CSU_DMAADDRL0 + offset) = addrSrc & 0xFFFFFFFF; VIR_ADDR_VAL(virMemAddr, AP_CSU_DMAADDRH0 + offset) = addrSrc >> 32; VIR_ADDR_VAL(virMemAddr, AP_CSU_DMASIZEGRANALLNUM0 + offset) = (0xF<<28) | dataLen; // dst reg VIR_ADDR_VAL(virMemAddr, AP_CSU_DMAADDRL1 + offset) = addrDst & 0xFFFFFFFF; VIR_ADDR_VAL(virMemAddr, AP_CSU_DMAADDRH1 + offset) = addrDst >> 32; VIR_ADDR_VAL(virMemAddr, AP_CSU_DMASIZEGRANALLNUM1 + offset) = (0xE<<24) | dataLen; // write global, size=0 VIR_ADDR_VAL(virMemAddr, AP_CSU_CMDHIGHDATA) = 0; stCsuDmaCmdL dmaCmdL; dmaCmdL.dmaType = 1; dmaCmdL.idSrc = 0 + (regGroup<<1); dmaCmdL.idDst = 1 + (regGroup<<1); dmaCmdL.dmaTag = tag; //(uint32_t)(VIR_ADDR_VAL(virMemAddr, AP_CSU_CMDFIFO0+(fifoNum<<2))) = (uint32_t)(*((uint32_t*)(&dmaCmdL))); memcpy((uint32_t*)(virMemAddr+AP_CSU_CMDFIFO0+(fifoNum<<2)), (uint32_t*)(&dmaCmdL), 4); return tag; }