Part Number:TMS320F28377D
如题所示,当我一次写入37250个16bit的数据,调试正常如下

当我一次性写入50000个16bit的数据,调试界面如下,调试窗口的变量不进行更新

当我一次性写入80000个16bit的数据,程序直接崩溃,无法开始运行,只能暂停或者结束调试

我的程序流程大概如下:28377对两块SRAM实现乒乓操作:CPU1首先对SRAM1进行写入数据,然后同时CPU2对SRAM2进行数据读取并写入,然后CPU1对SRAM2进行写入数据,同时CPU2对SRAM1进行数据读取并写入,只是一个简单的乒乓操作,代码如下,请问是什么问题呢??很急!!!!辛苦尽快给我参考意见,感谢!!!
CPU1代码
#include "device.h"
#include "F28x_Project.h"
#include "board.h"
#include <driverlib.h>
#define ASRAM_CS2_START_ADDR 0x100000//手册规定CS2起始地址
#define ASRAM_CS3_START_ADDR 0x300000//与FPGA通信
#define ASRAM_CS4_START_ADDR 0x380000
#define data_length 80000//测试的单次写入极限
void data_write(void);
void initEMIFA(void);
void setupEMIF1PinmuxAsync16Bit(void);
EMIF_AsyncTimingParams tparam;
//数据缓存数组
uint16_t data_CS2[data_length] = {0};//存储的均为字(Word,16bit)
uint16_t data_CS4[data_length] = {0};
//IPC通信变量
IPC_MessageQueue_t messageQueue;
IPC_Message_tTxMsg, RxMsg;
uint16_t current_buffer=0;//0-CS2 1-CS4
#pragma DATA_SECTION(data_CS2,"data_CS2");
#pragma DATA_SECTION(data_CS4,"data_CS4");
/**
* main.c
*/
void main(void)
{int i=0;Device_init(); // Initialize device clock and peripheralsDevice_initGPIO(); // Initialize GPIO and configure the GPIO pin as a push-pull outputInterrupt_initModule(); // Initialize PIE and clear PIE registers. Disables CPU interrupts.IER = 0x0000; //CPU级中断使能IFR = 0x0000; //清除CPU级中断标志Interrupt_initVectorTable(); // Initialize the PIE vector table with pointers to ISRBoard_init();//启动CPU2代码#ifdef _STANDALONE#ifdef _FLASH// Send boot command to allow the CPU02 application to begin execution//IPCBootCPU2(C1C2_BROM_BOOTMODE_BOOT_FROM_FLASH);//这是bit-field库IPC_setBootMode(IPC_CPU1_L_CPU2_R, C1C2_BROM_BOOTMODE_BOOT_FROM_FLASH);#else// Send boot command to allow the CPU02 application to begin execution//IPCBootCPU2(C1C2_BROM_BOOTMODE_BOOT_FROM_RAM);IPC_setBootMode(IPC_CPU1_L_CPU2_R, C1C2_BROM_BOOTMODE_BOOT_FROM_RAM);#endif#endif//// Clear any IPC flags if set already//IPC_clearFlagLtoR(IPC_CPU1_L_CPU2_R, IPC_FLAG_ALL);//// Initialize message queue//IPC_initMessageQueue(IPC_CPU1_L_CPU2_R, &messageQueue, IPC_INT1, IPC_INT1);//// Synchronize both the cores//IPC_sync(IPC_CPU1_L_CPU2_R, SYNC_FLAG);EINT; // Enable Global Interrupt (INTM)ERTM; // Enable real-time interrupt (DBGM)initEMIFA();TxMsg.command = 0;TxMsg.address = 0;
//TxMsg.dataw1 = current_buffer;//当前的缓冲区 0:CS2_SRAM 1:CS4_SRAMTxMsg.dataw2 = 1;//校验,看数据传输是否正确for (;;){EMIF_selectMaster(EMIF1CONFIG_BASE, EMIF_MASTER_CPU1_G);//CPU1独占 CPU2只能读不能写//实时更新current_buffer的值TxMsg.dataw1 = current_buffer;//当前的缓冲区 0:CS2_SRAM 1:CS4_SRAMdata_write();//CPU1写入SRAMEMIF_selectMaster(EMIF1CONFIG_BASE, EMIF_MASTER_CPU1_NG);//CPU1NG CPU2可以选为主控IPC_sendMessageToQueue(IPC_CPU1_L_CPU2_R, &messageQueue, IPC_ADDR_CORRECTION_ENABLE,&TxMsg, IPC_BLOCKING_CALL);GPIO_togglePin(myGPIO99);DELAY_US(1000000);}
}
/*
* CS2_SRAM、CS4_SRAM交替写入5555、AAAA
*调用次数current_buffer 操作SRAM 写入值(修正后)10CS20x555521CS40x555530CS20xAAAA41CS40xAAAA
*
*/
void data_write(void)
{int i=0;static int CS2=0;//0-5555 1-AAAAstatic int CS4=0;//0-5555 1-AAAA//模拟发送的递增数据uint16_t increaseData = 0;//乒乓if(current_buffer==0){if(CS2==0){for(i=0;i<data_length;i++){data_CS2[i]=0x5555;}}else{for(i=0;i<data_length;i++){data_CS2[i]=0xAAAA;}}CS2 ^= 1;}else{if(CS4==0){for(i=0;i<data_length;i++){data_CS4[i]=0x5555;}}else{for(i=0;i<data_length;i++){data_CS4[i]=0xAAAA;}}CS4 ^= 1;}//此处使用异或 不同为1 相同为0//切换缓冲区current_buffer ^= 1;
}
void setupEMIF1PinmuxAsync16Bit(void)
{uint16_t i;GPIO_setPinConfig(GPIO_28_EM1CS4N);GPIO_setPinConfig(GPIO_29_EM1SDCKE);GPIO_setPinConfig(GPIO_30_EM1CLK);GPIO_setPinConfig(GPIO_31_EM1WEN);
//GPIO_setPinConfig(GPIO_32_EM1CS0N);//CS0只能用于SDRAM,电路图连接的SRAM1,无法使用GPIO_setPinConfig(GPIO_33_EM1RNW);GPIO_setPinConfig(GPIO_34_EM1CS2N);GPIO_setPinConfig(GPIO_35_EM1CS3N);GPIO_setPinConfig(GPIO_36_EM1WAIT);GPIO_setPinConfig(GPIO_37_EM1OEN);//// Selecting address lines.//GPIO_setPinConfig(GPIO_38_EM1A0);GPIO_setPinConfig(GPIO_39_EM1A1);GPIO_setPinConfig(GPIO_40_EM1A2);GPIO_setPinConfig(GPIO_41_EM1A3);GPIO_setPinConfig(GPIO_44_EM1A4);GPIO_setPinConfig(GPIO_45_EM1A5);GPIO_setPinConfig(GPIO_46_EM1A6);GPIO_setPinConfig(GPIO_47_EM1A7);GPIO_setPinConfig(GPIO_48_EM1A8);GPIO_setPinConfig(GPIO_49_EM1A9);GPIO_setPinConfig(GPIO_50_EM1A10);GPIO_setPinConfig(GPIO_51_EM1A11);GPIO_setPinConfig(GPIO_52_EM1A12);GPIO_setPinConfig(GPIO_86_EM1A13);GPIO_setPinConfig(GPIO_87_EM1A14);GPIO_setPinConfig(GPIO_88_EM1A15);GPIO_setPinConfig(GPIO_89_EM1A16);GPIO_setPinConfig(GPIO_90_EM1A17);//// Selecting data lines.//21-16都没用,电路采用的SRAM是16bit的,只需要D0-D15即可GPIO_setPinConfig(GPIO_63_EM1D21);GPIO_setPinConfig(GPIO_64_EM1D20);GPIO_setPinConfig(GPIO_65_EM1D19);GPIO_setPinConfig(GPIO_66_EM1D18);GPIO_setPinConfig(GPIO_67_EM1D17);GPIO_setPinConfig(GPIO_68_EM1D16);GPIO_setPinConfig(GPIO_69_EM1D15);GPIO_setPinConfig(GPIO_70_EM1D14);GPIO_setPinConfig(GPIO_71_EM1D13);GPIO_setPinConfig(GPIO_72_EM1D12);GPIO_setPinConfig(GPIO_73_EM1D11);GPIO_setPinConfig(GPIO_74_EM1D10);GPIO_setPinConfig(GPIO_75_EM1D9);GPIO_setPinConfig(GPIO_76_EM1D8);GPIO_setPinConfig(GPIO_77_EM1D7);GPIO_setPinConfig(GPIO_78_EM1D6);GPIO_setPinConfig(GPIO_79_EM1D5);GPIO_setPinConfig(GPIO_80_EM1D4);GPIO_setPinConfig(GPIO_81_EM1D3);GPIO_setPinConfig(GPIO_82_EM1D2);GPIO_setPinConfig(GPIO_83_EM1D1);GPIO_setPinConfig(GPIO_85_EM1D0);//// Setting DQM and Bank Select lines.//
//GPIO_setPinConfig(GPIO_88_EM1DQM0);//复用为地址线
//GPIO_setPinConfig(GPIO_89_EM1DQM1);//复用为地址线
//GPIO_setPinConfig(GPIO_90_EM1DQM2);//复用为地址线
//GPIO_setPinConfig(GPIO_91_EM1DQM3);//复用为地址线GPIO_setPinConfig(GPIO_92_EM1BA1);GPIO_setPinConfig(GPIO_93_EM1BA0);GPIO_setPinConfig(GPIO_94_EM1A21);//// Setup async mode and enable pull-ups for Data pins.// GPIO84电路有上拉?什么作用?for(i=69; i<=85;i++){if(i != 84){GPIO_setPadConfig(i, GPIO_PIN_TYPE_PULLUP);GPIO_setQualificationMode(i, GPIO_QUAL_ASYNC);}}
}
/*
* EMIF1CLK = CPU1SYSCLK
* 无访问保护
*/
void initEMIFA(void)
{//// Configure to run EMIF1 on full Rate. (EMIF1CLK = CPU1SYSCLK)//SysCtl_setEMIF1ClockDivider(SYSCTL_EMIF1CLK_DIV_1);//不分频//// Grab EMIF1 For CPU1.// 是否可以CPU1写CPU2读?grab是什么意思EMIF_selectMaster(EMIF1CONFIG_BASE, EMIF_MASTER_CPU1_G);//CPU1独占 CPU2只能读不能写//// Disable Access Protection. (CPU_FETCH/CPU_WR/DMA_WR)//EMIF_setAccessProtection(EMIF1CONFIG_BASE, 0x0);//000 无访问保护//// Commit the configuration related to protection. Till this bit remains// set, contents of EMIF1ACCPROT0 register can't be changed.//EMIF_commitAccessConfig(EMIF1CONFIG_BASE);//// Lock the configuration so that EMIF1COMMIT register can't be changed// any more.//EMIF_lockAccessConfig(EMIF1CONFIG_BASE);//// Configure GPIO pins for EMIF1.//setupEMIF1PinmuxAsync16Bit();//为什么有些注释掉?//// Configures Normal Asynchronous Mode of Operation.// 配置 为 异步正常模式。EMIF_setAsyncMode(EMIF1_BASE, EMIF_ASYNC_CS2_OFFSET,EMIF_ASYNC_NORMAL_MODE);EMIF_setAsyncMode(EMIF1_BASE, EMIF_ASYNC_CS3_OFFSET,EMIF_ASYNC_NORMAL_MODE);EMIF_setAsyncMode(EMIF1_BASE, EMIF_ASYNC_CS4_OFFSET,EMIF_ASYNC_NORMAL_MODE);//// Disables Extended Wait Mode.// 禁用 扩展等待模式:即,访问超时时间是固定的,不会因为等待信号延长。EMIF_disableAsyncExtendedWait(EMIF1_BASE, EMIF_ASYNC_CS2_OFFSET);EMIF_disableAsyncExtendedWait(EMIF1_BASE, EMIF_ASYNC_CS3_OFFSET);EMIF_disableAsyncExtendedWait(EMIF1_BASE, EMIF_ASYNC_CS4_OFFSET);//// Configure EMIF1 Data Bus Width.// 设置 数据总线宽度为 16 位EMIF_setAsyncDataBusWidth(EMIF1_BASE, EMIF_ASYNC_CS2_OFFSET,EMIF_ASYNC_DATA_WIDTH_16);EMIF_setAsyncDataBusWidth(EMIF1_BASE, EMIF_ASYNC_CS3_OFFSET,EMIF_ASYNC_DATA_WIDTH_16);EMIF_setAsyncDataBusWidth(EMIF1_BASE, EMIF_ASYNC_CS4_OFFSET,EMIF_ASYNC_DATA_WIDTH_16);//// Configure the access timing for CS2 space.// 配置 读写时序参数tparam.rSetup = 0;tparam.rStrobe = 14;
//tparam.rStrobe = 3;
//tparam.rHold = 0;tparam.rHold = 1;tparam.turnArnd = 1;tparam.wSetup = 0;tparam.wStrobe = 14;tparam.wHold = 0;EMIF_setAsyncTimingParams(EMIF1_BASE, EMIF_ASYNC_CS2_OFFSET, &tparam);EMIF_setAsyncTimingParams(EMIF1_BASE, EMIF_ASYNC_CS3_OFFSET, &tparam);EMIF_setAsyncTimingParams(EMIF1_BASE, EMIF_ASYNC_CS4_OFFSET, &tparam);
}
CPU2代码
#include "device.h"
#include "F28x_Project.h"
#include "board.h"
#include <driverlib.h>
#define ASRAM_CS2_START_ADDR 0x100000//手册规定CS2起始地址
#define ASRAM_CS3_START_ADDR 0x300000//与FPGA通信
#define ASRAM_CS4_START_ADDR 0x380000
#define data_length 80000
EMIF_AsyncTimingParams tparam;
//数据缓存数组
uint16_t data_CS2_CPU2[data_length] = {0};//存储的均为字(Word,16bit)
uint16_t data_CS4_CPU2[data_length] = {0};
uint16_t CS2;
uint16_t CS4;
bool status = false;
IPC_MessageQueue_t messageQueue;
IPC_Message_t TxMsg, RxMsg;
uint16_t IPCCount;
volatile uint16_t dataReadyFlag = 0;//CPU1发消息确认FLAG
volatile uint16_t dataSource = 0; // 0: CS4_SRAM, 1: CS2_SRAM 与CPU1相反避免BUFFER冲突
#pragma DATA_SECTION(data_CS2_CPU2,"data_CS2_CPU2");
#pragma DATA_SECTION(data_CS4_CPU2,"data_CS4_CPU2");
__interrupt void IPC_1_ISR(void);
/**
* main.c
*/
void main(void)
{int i=0;Device_init(); // Initialize device clock and peripheralsDevice_initGPIO(); // Initialize GPIO and configure the GPIO pin as a push-pull outputInterrupt_initModule(); // Initialize PIE and clear PIE registers. Disables CPU interrupts.IER = 0x0000; //CPU级中断使能IFR = 0x0000; //清除CPU级中断标志Interrupt_initVectorTable(); // Initialize the PIE vector table with pointers to ISRBoard_init();//// Clear any IPC flags if set already//IPC_clearFlagLtoR(IPC_CPU2_L_CPU1_R, IPC_FLAG_ALL);//// Initialize message queue//IPC_initMessageQueue(IPC_CPU2_L_CPU1_R, &messageQueue, IPC_INT1, IPC_INT1);//// Synchronize both the cores.//IPC_sync(IPC_CPU2_L_CPU1_R, SYNC_FLAG);EINT; // Enable Global Interrupt (INTM)ERTM; // Enable real-time interrupt (DBGM)for (;;){if (dataReadyFlag){dataReadyFlag = 0; // 清除标志if (dataSource == 0){// 从 CS4_SRAM 中读取数据进行运算 与CPU1相反避免BUFFER冲突//processDataFromCS2();//现在只是读取数组中的一个元素//问题:怎么直接调用CPU1写入的数组,若是CPU2读取再写入涉及到主控权的更换,现在只读取了一个数据//跑通之后,CPU1写完数据即可尝试释放主控(CPU1_NG),CPU2再次获取主控进行读取和写入再释放主控(CPU1_NG),借用例程的写法CS4=*((uint16_t*)ASRAM_CS4_START_ADDR);//(uint16_t*)把地址强转为uint16_tfor(i=0;i<data_length;i++){data_CS2_CPU2[i]=*(((uint16_t*)ASRAM_CS2_START_ADDR)+i);}
//data_CS4[0]=1;}else{// 从 CS2_SRAM 中读取数据进行运算//processDataFromCS4();CS2=*((uint16_t*)ASRAM_CS2_START_ADDR);//(uint16_t*)把地址强转为uint16_t
//data_CS2[0]=1;for(i=0;i<data_length;i++){data_CS4_CPU2[i]=*(((uint16_t*)ASRAM_CS4_START_ADDR)+i);}}EMIF_selectMaster(EMIF1CONFIG_BASE, EMIF_MASTER_CPU1_NG);//CPU1NG CPU1可以选为主控}}
}
//
// IPC ISR for Flag 1
// C28x core sends data with message queue using Flag 0
//
__interrupt void IPC_1_ISR(void)
{EMIF_selectMaster(EMIF1CONFIG_BASE, EMIF_MASTER_CPU2_G);//CPU2独占 CPU1只能读不能写//// Read the message from the message queue//IPC_readMessageFromQueue(IPC_CPU2_L_CPU1_R, &messageQueue, IPC_ADDR_CORRECTION_ENABLE,&RxMsg, IPC_NONBLOCKING_CALL);if(RxMsg.dataw2 == 1){status = true;dataSource = RxMsg.dataw1;//获取CPU1的currentbufferdataReadyFlag = 1;}IPCCount++;//// Send response message//
//TxMsg.command = IPC_CMD_RESP;
//TxMsg.address = 0; // Not used
//TxMsg.dataw1 = status ? TEST_PASS : TEST_FAIL;
//TxMsg.dataw2 = RxMsg.dataw2; // Use the message identifier from the received message
//
//IPC_sendMessageToQueue(IPC_CPU2_L_CPU1_R, &messageQueue, IPC_ADDR_CORRECTION_DISABLE,
//&TxMsg, IPC_NONBLOCKING_CALL);//// Acknowledge the flag//IPC_ackFlagRtoL(IPC_CPU2_L_CPU1_R, IPC_FLAG1);//// Acknowledge the PIE interrupt.//Interrupt_clearACKGroup(INTERRUPT_ACK_GROUP1);
}
Lydia:
您好,
已经收到了您的案例,调查需要些时间,感谢您的耐心等待。
,
zhisheng xiong:
你好,程序卡死的问题解决了,但是程序崩溃的原因还没找到,数组一旦超过65536就会崩溃,调试的时候无法运行程序,主动给他暂停之后CPU1和CPU2程序都会卡在下图所示位置中
一直卡在这个for循环,请问这是什么语句?会不会是这个length上限是65536?length的定义我看是length_t,但是length_t找不到定义
,
Taylor:
这个需要你自己调试来找具体原因。可以将变量类型改为32位无符号整数等试一下。
单步执行,设置断点跟进。debug不行的话可以加log运行。
,
zhisheng xiong:
但是现在的问题就是没法调试,因为数组为80000的时候都没进入main函数,无法运行程序,主动给他暂停之后CPU1和CPU2程序都会卡在下图所示位置中
,
Taylor:
上面已经给出建议了,初次之外没有其他便捷方法了。
,
zhisheng xiong:
请问加log运行是什么意思呢??程序崩溃也可以用吗?
TI中文支持网




