DSP- 6678--------- SRIO通信(1)系统结构

一、概述

本设计的设计流程如图所示

1 主核创建messageQ(master)

2 发送起始标志信号至FPGA(nwrite)

3 FPGA收到信号之后,通过SWRITE的方式向DSP写数据

4 FPGA写完数据之后,发送doorbell,触发DSP doorbell中断

5 在doorbell中断中释放信号量 开始进行数据处理

6 DSP打开从核创建的messageQ(slave)  并将各自需要的数据通过messageQ发送给各个从核

7 从核接收主核发送来的messageQ(slave) 进行数据处理

8 处理完毕之后 发送messageQ(master)至主核

9 主核接收到从核发送的messageQ(slave)之后,通过SWRITE的方式发送数据至FPGA 




二、cfg文件

主要定义doorbell中断函数以及信号量

//创建SRIO doorbell硬件中断
var hwi0Params = new Hwi.Params();
hwi0Params.instance.name = "hwi0";
hwi0Params.eventId = 0x14; //CSL_GEM_INTDST_N_PLUS_16
Program.global.hwi0 = Hwi.create(4, "&SRIO_Doorbell_ISR", hwi0Params);


//创建信号量
Sem.supportsEvents = false;
Program.global.sem_db   = Sem.create(0);

定义初始化入口函数

Startup.firstFxns.$add('&system_init');

三、main函数

3.1 系统初始化 system_init

void system_init(void)
{
	if(DNUM == 0)
	{
		TSC_init();	//initialize TSC to measure cycle

		// System init
		CACHE_setL1PSize(CACHE_L1_32KCACHE);
		CACHE_setL1DSize(CACHE_L1_32KCACHE);
		CACHE_setL2Size(CACHE_0KCACHE);
		CACHE_invAllL1p(CACHE_WAIT);
		CACHE_wbInvAllL1d(CACHE_WAIT);

		//DSP core speed: 100*10/1=1000MHz
		KeyStone_main_PLL_init(100, 10, 1);
		KeyStone_PASS_PLL_init(100, 21, 2);

		//DDR init 66.66667*20/1= 1333
		KeyStone_DDR_init (66.66667, 20, 1, NULL);

		/* protect L1 as cache */
		L1_cache_protection();

		/*enable L1P ED and scrub whole L1P*/
		L1P_EDC_setup();

		/*enable LL2 EDC and scrub whole LL2*/
		LL2_EDC_setup();

		/*Enable MSMC EDC and setup scrubbing cycle counter= 255*1024*/
		KeyStone_SL2_EDC_enable(255);
	}
}

3.2 初始化队列名称

int mc_process_init (int number_of_cores)
{
    int i;
    /* Generate queue names based on own proc ID and total number of procs */
    System_sprintf(localQueueName, "%s",MultiProc_getName(MultiProc_self()));
    System_sprintf(masterQueueName,"%s",MASTER_QUEUE_NAME);

    for(i = 0;i < number_of_cores; i++)
    {
    	System_sprintf(slaveQueueName[i], "%s",  MultiProc_getName(i));  //返回i核的名字
    }

    return 0;
}

3.3 SRIO初始化

srio_init(312.5,0xAA,3.125,PATH_4xLaneABCD);
void srio_init(float inputRefClock_MHz,unsigned int localId,float linkSpeed_GHz,SRIO_Path_CTL pathMode)
{
	serdes_cfg.commonSetup.inputRefClock_MHz = inputRefClock_MHz;  //参考时钟

	memset(&srio_cfg, 0, sizeof(srio_cfg));

	srio_cfg.blockEn.bBLK1_LSU_EN= 1;
	srio_cfg.blockEn.bBLK2_MAU_EN= 1;
	srio_cfg.blockEn.bBLK3_TXU_EN= 1;
	srio_cfg.blockEn.bBLK4_RXU_EN= 1;
	srio_cfg.srio_1x2x4x_path_control = get_path_cfg(pathMode); //设置SRIO几根线
	srio_cfg.loopback_mode = SRIO_NO_LOOPBACK;  //设置SRIO模式
	srio_identify_used_ports_lanes(srio_cfg.srio_1x2x4x_path_control);//通道数确认

	srio_cfg.device_ID_routing_config = dsp0_device_ID_routing_config; 
	srio_cfg.uiNumDeviceId	= sizeof(dsp0_device_ID_routing_config)/sizeof(SRIO_Device_ID_Routing_Config);//8

	serdes_cfg.commonSetup.loopBandwidth = SERDES_PLL_LOOP_BAND_MID;
	srio_cfg.serdes_cfg					 = &serdes_cfg;

	serdesLinkSetup.txOutputSwing    = 15; /*0~15 represents between 100 and 850 mVdfpp  */
	serdesLinkSetup.testPattern      = SERDES_TEST_DISABLED;
	serdesLinkSetup.rxAlign          = SERDES_RX_COMMA_ALIGNMENT_ENABLE;
	serdesLinkSetup.rxInvertPolarity = SERDES_RX_NORMAL_POLARITY;
	serdesLinkSetup.rxTermination    = SERDES_RX_TERM_COMMON_POINT_AC_COUPLE;
	serdesLinkSetup.rxEqualizerConfig= SERDES_RX_EQ_ADAPTIVE;
	serdesLinkSetup.rxCDR            = SERDES_RX_CDR_1;
	serdesLinkSetup.txInvertPolarity = SERDES_TX_NORMAL_POLARITY;
	serdesLinkSetup.linkSpeed_GHz	 = linkSpeed_GHz;


	srio_cfg.msg_cfg  = &msg_cfg;

	KeyStone_SRIO_Init(&srio_cfg);

}

主要设置SRIO相关参数,速度、lane数、本地ID等相关参数。

3.4 创建任务

    /* Create a unique 'master' Task if on proc 0 */
    Task_Params_init(&params);
    params.stackSize = 0x2000;
    if (MultiProc_self() == 0) //核0执行主任务
    {
        Task_create(master_main, &params, NULL);
    }

    Task_create(slave_main, &params, NULL); //其余核执行从任务

分别创建主核和从核的任务函数 master_main,  slave_main

3.5 BIOS_start( )

猜你喜欢

转载自blog.csdn.net/yunge812/article/details/80908947