中级会员
- 积分
- 254
- 金钱
- 254
- 注册时间
- 2020-10-19
- 在线时间
- 54 小时
|
楼主 |
发表于 2024-1-3 16:15:31
|
显示全部楼层
昨天尝试了一下加入延时,虽然能够实现进入软中断,但由于要测试核间利用OCM的通信速率,测试结果为6Mbps。并且时间上还和延时有关,低于80ms,cpu1就无法进入中断。这种方式应该是不太对的。所以问题并没有解决。这是我的代码,望有大佬出没,能帮忙看看具体是哪里出了问题。
- #include "xparameters.h"
- #include "xscugic.h"
- #include "xil_printf.h"
- #include "xil_exception.h"
- #include "xil_mmu.h"
- #include "stdio.h"
- #include <string.h>
- #include <stdint.h>
- #include <stdlib.h>
- #include <sleep.h>
- #include <time.h>
- //宏定义
- #define INTC_DEVICE_ID XPAR_SCUGIC_SINGLE_DEVICE_ID //中断ID
- #define SHARE_BASE 0xffff0000 //共享OCM首地址
- #define CPU1_START_ADDR 0xfffffff0 //CPU1开始地址
- #define CPU1_START_MEM 0x10000000 //CPU1程序开始地址
- #define CPU1_ID XSCUGIC_SPI_CPU1_MASK //CPU1 ID,0bxxxxxx1x指向CPU1
- //"SEV"指令唤醒CPU1并跳转至相应的程序
- #define sev() __asm__("sev")
- //堆空间开辟长度64KB(16384*4)
- #define ALLOCATE_HEAP_SPACE 16384
- //函数声明
- void start_cpu1();
- void cpu0IntrInit(XScuGic *intc_ptr);
- void IntrHandler(void *CallbackRef);
- //全局变量
- XScuGic Intc; //中断控制器驱动
- volatile int rec_intr_flag = 0; //接收到来自cpu1中断的标志
- //软件中断号
- u16 SoftIntrIdToCpu0 = 0 ;
- u16 SoftIntrIdToCpu1 = 1 ;
- //CPU0 main函数
- int main()
- {
- //用于验证cpu0是否成功发送软中断给cpu1
- uint32_t u32SoftIntrFlag = 1;
- //开辟64KB堆空间并初始化
- uint32_t* pu32HeapSpace = (uint32_t*)calloc(ALLOCATE_HEAP_SPACE,sizeof(uint32_t));
- if(NULL != pu32HeapSpace)
- {
- for(uint32_t i = 0; i < ALLOCATE_HEAP_SPACE; i++)
- {
- pu32HeapSpace[i] = i;
- }
- xil_printf("Heap initialization is complete! \r\n");
- }
- else
- {
- xil_printf("Allocate Heap Space is failed.\r\n");
- return 1;
- }
- //复位使用的OCM空间
- uint32_t* pToOCM = (uint32_t*)SHARE_BASE;
- memset(pToOCM, 0, sizeof(ALLOCATE_HEAP_SPACE));
- //禁用Cache缓存
- Xil_SetTlbAttributes(SHARE_BASE,0x14de2);
- //禁用 0xfffffff0 的 Cache 属性
- Xil_SetTlbAttributes(CPU1_START_ADDR,0x14de2);
- //启动CPU1
- start_cpu1();
- //CPU0中断初始化
- cpu0IntrInit(&Intc);
- while(1)
- {
- if(rec_intr_flag == 0)
- {
- xil_printf("CPU0: Prepare to Write Heap Data to COM. \r\n");
- //将参数写入共享的内存
- for(uint32_t j = 0; j < ALLOCATE_HEAP_SPACE; j++)
- {
- Xil_Out32((SHARE_BASE + j*4),pu32HeapSpace[j]);
- }
- xil_printf("CPU0: Write Complete. \r\n");
- // free(pu32HeapSpace);
- xil_printf("\r\n");
- Again:
- usleep(80*1000); //延时100ms
- //给CPU1发送软件中断
- u32SoftIntrFlag = XScuGic_SoftwareIntr(&Intc,SoftIntrIdToCpu1,CPU1_ID);
- if(XST_SUCCESS == u32SoftIntrFlag)
- {
- xil_printf("CPU0: SoftwareInter to CPU1 is success! \r\n");
- rec_intr_flag = 1;
- }
- else
- {
- xil_printf("CPU0: Retry to SoftwareInter to CPU1! \r\n");
- goto Again;
- }
- }
- }
- return 0 ;
- }
- //启动CPU1
- void start_cpu1()
- {
- //向 CPU1_START_ADDR(0Xffffffff0)地址写入 CPU1 的访问内存基地址
- Xil_Out32(CPU1_START_ADDR, CPU1_START_MEM);
- dmb();
- sev(); //唤醒CPU1并跳转至相应的程序
- }
- //CPU0中断初始化
- void cpu0IntrInit(XScuGic *intc_ptr)
- {
- //初始化中断控制器
- XScuGic_Config *intc_cfg_ptr;
- intc_cfg_ptr = XScuGic_LookupConfig(INTC_DEVICE_ID);
- XScuGic_CfgInitialize(intc_ptr, intc_cfg_ptr,
- intc_cfg_ptr->CpuBaseAddress);
- //设置并打开中断异常处理功能
- Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_INT,
- (Xil_ExceptionHandler)XScuGic_InterruptHandler, intc_ptr);
- Xil_ExceptionEnable();
- //关联中断源及中断处理函数
- XScuGic_Connect(intc_ptr, SoftIntrIdToCpu0,
- (Xil_ExceptionHandler)IntrHandler, (void *)intc_ptr);
- XScuGic_Enable(intc_ptr, SoftIntrIdToCpu0); //CPU0软件中断
- }
- //中断服务函数
- void IntrHandler(void *CallbackRef)
- {
- xil_printf("This is CPU0,Receive software interrupt from CPU1\r\n");
- xil_printf("\r\n");
- rec_intr_flag = 0;
- }
- 以上是cpu0.c
- /*
- * Arm1.c
- *
- * Created on: 2023年12月29日
- * Author: yuan.lv
- */
- #include "xparameters.h"
- #include "xscugic.h"
- #include "xil_printf.h"
- #include "xil_exception.h"
- #include "xil_mmu.h"
- #include "stdio.h"
- //宏定义
- #define INTC_DEVICE_ID XPAR_SCUGIC_SINGLE_DEVICE_ID //中断ID
- #define SHARE_BASE 0xffff0000 //共享OCM首地址
- #define CPU0_ID XSCUGIC_SPI_CPU0_MASK //CPU1 ID,0bxxxxxxx1指向CPU0
- //堆空间开辟长度64KB(16384*4)
- #define ALLOCATE_HEAP_SPACE 16384
- //函数声明
- void cpu1IntrInit(XScuGic *intc_ptr);
- void IntrHandler(void *CallbackRef);
- //全局变量
- XScuGic Intc; //中断控制器驱动
- volatile int intr_flag = 0; //软件中断的标志
- //软件中断号
- u16 SoftIntrIdToCpu0 = 0 ;
- u16 SoftIntrIdToCpu1 = 1 ;
- //CPU1 main函数
- int main()
- {
- //存储从ocm中读出的数据
- volatile uint32_t u32ReadData = 0;
- //禁用Cache缓存
- Xil_SetTlbAttributes(SHARE_BASE,0x14de2);
- //CPU1中断初始化
- cpu1IntrInit(&Intc);
- while(1)
- {
- if(intr_flag)
- {
- xil_printf("CUP1: Prepare to Read Data from COM. \r\n");
- for(uint32_t i = 0; i < ALLOCATE_HEAP_SPACE; i++)
- {
- u32ReadData = Xil_In32(SHARE_BASE + i*4); //从共享内存中读出数据
- xil_printf("CPU1: Read Data [No.%d 0x%x] \r\n", i, u32ReadData);
- }
- xil_printf("CUP1: Read Complete. \r\n");
- xil_printf("\r\n");
- //给CPU0发送软件中断
- XScuGic_SoftwareIntr(&Intc,SoftIntrIdToCpu0,CPU0_ID);
- intr_flag = 0;
- }
- }
- return 0 ;
- }
- //CPU1中断初始化
- void cpu1IntrInit(XScuGic *intc_ptr)
- {
- //初始化中断控制器
- XScuGic_Config *intc_cfg_ptr;
- intc_cfg_ptr = XScuGic_LookupConfig(INTC_DEVICE_ID);
- XScuGic_CfgInitialize(intc_ptr, intc_cfg_ptr,
- intc_cfg_ptr->CpuBaseAddress);
- //设置并打开中断异常处理功能
- Xil_ExceptionRegisterHandler(XIL_EXCEPTION_ID_INT,
- (Xil_ExceptionHandler)XScuGic_InterruptHandler, intc_ptr);
- Xil_ExceptionEnable();
- //关联中断源及中断处理函数
- XScuGic_Connect(intc_ptr, SoftIntrIdToCpu1,
- (Xil_ExceptionHandler)IntrHandler, (void *)intc_ptr);
- XScuGic_Enable(intc_ptr, SoftIntrIdToCpu1); //使能CPU1软件中断
- }
- //中断服务函数
- void IntrHandler(void *CallbackRef)
- {
- xil_printf("This is CUP1,Soft Interrupt from CPU0\r\n") ;
- intr_flag = 1;
- }
- 以上是cpu1.c
复制代码 |
|