This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
调用 Fapi_issueAppoanoudCommandWithAddress()返回 Fapi_Status_Success,但运行 Fapi_doBlankCheck()时显示未发生擦除。
在调用擦除后、我确实有一个 while ()循环等待检查就绪。
在闪存 API 手册中、可以看到这一点
请注意、闪存 API 函数不配置任何 DCSM 寄存器。 用户应用程序应确保配置所需的 DCSM 设置。 例如、如果一个区域是受保护的、那么为了能够擦除或者编辑那个区域的闪存扇区、闪存 API 应该从同一个区域执行。 或者区域应被解锁。 否则,闪存 API 对闪存寄存器的写入将不会成功。 闪存 API 不会检查对闪存寄存器的写入是否正在进行。 它按照擦除/编程序列的要求写入它们、并在写入完成后返回。 这将导致闪存 API 返回错误的成功状态。 例如,调用 Fapi_issueCommandWithAddress (Fapi_EraseSector,Address)时,可以返回成功状态,但这并不意味着扇区擦除成功。
但我没有设置安全、使用 C2Prog 和 Codeskin 引导加载程序、我可以很好地对 CPU1进行编程。
是否有任何其他需要设置的条件来允许擦除?
Tonyo、
1)
在调用擦除函数之前、请检查 EALLOW 是否被执行。 它应该被执行。
在闪存擦除操作之前、请检查闪存泵信号量是否被正确获得。 在对其组执行编程/擦除操作之前、泵信号量应由相应的内核获得。
2)
如果上述内容不能帮助解决问题、请搜索"当闪存 API 无法擦除或编程时、我们可以考虑哪些常见的调试提示?" 在 https://e2e.ti.com/support/microcontrollers/c2000-microcontrollers-group/c2000/f/c2000-microcontrollers-forum/951668/faq-faq-on-flash-api-usage-for-c2000-devices 上的闪存 API 常见问题解答中
3)
在上述常见问题解答中、请搜索以下问题并阅读答案。
完成扇区擦除操作后、Fapi_issueAppeApphexCommandAddress (Fapi_EraseSector、xx)函数调用是否返回?
如果 Fapi_issueAppiCommandWithAddress (Fapi_EraseSector、xx)没有等待擦除操作完成、我们如何知道擦除操作是否成功?
如果上述建议对解决该问题没有帮助、请告诉我。
谢谢、此致、
Vamsi
是的、我相信我已经正确设置了一些内容、下面是相关代码、其中显示使用了 EALLOW/EDIS、还有一个 while ()循环用于测试 FsmReady、还有一个循环用于确保闪存泵为自有设备:
--开始----
EALLOW;//泵和 API 需要
//控制闪存泵
int pump_ID = 0;
CPU1
PUMP_ID = 0x2;
#Elif Defined (CPU2)
PUMP_ID = 0x1;
#endif
while (FlashPumpSemaphoreRegs.PUMPREQUEST.bit.PUMP_RUSE!= PUMP_ID)
{
FlashPumpSemaphoreRegs.PUMPREQUEST.ALL = IPC_PUMP_KEY | PUMP_ID;
}
//检查
if (((DcsmCommonRegs.FLSEM.bit.sem!= 0)&(DcsmCommonRegs.FLSEM.bit.sem!= 3))
{
//获取闪存包装程序区域信号量
Debug_printf ("FLASHPROG_eraseSectors:采用的包装器区域、0x%x\n\r"、DcsmCommonRegs.FLSEC.bit.sem);
返回 FLASHPROG_STATUS_UNLOCK_ERROR;
}
if (((DcsmCommonRegs.SECTSTAT.ALL 和0x3FFFFFFF)!= 0x3FFFFFFF)
{
//某些闪存扇区被分配给安全区域(不检查 bank1)
Debug_printf ("FLASHPROG_eraseSecitors:分配给安全区域的闪存扇区、0x%X\n\r\n、(DcsmCommonRegs.SECTSTAT.ALL 和0x3FFFFFFF));
返回 FLASHPROG_STATUS_UNLOCK_ERROR;
}
if (((DcsmCommonRegs.RAMSTAT.ALL 和0x0000FFFF)!= 0x0000FFFF)
{
//某些 RAM 扇区被分配给安全区域
Debug_printf ("FLASHPROG_eraseSecitors:分配给安全区域的 RAM 扇区、0x%X\n\r"、(DcsmCommonRegs.RAMSTAT.ALL 和0x0000FFFF);
返回 FLASHPROG_STATUS_UNLOCK_ERROR;
}
if (FlashPumpSemaphoreRegs.PUMPREQUEST.bit.PUMP_RUSE!= PUMP_ID)
{
Debug_printf ("FLASHPROG_eraseSecitors:FLASHPROG_STATUS_PUMP_ERROR、owner=%x\n"、FlashPumpSemaphoreRegs.PUMPREQUEST.bit.PUMP_Ownership);
返回 FLASHPROG_STATUS_PUMP_ERROR;
}
masks = mask;
I = 0;
状态= Fapi_Status_Success;
while ((掩码!= 0)&&(status = Fapi_Status_Success))
{
//如果我们到达此处,则仍有要擦除的扇区
//查找下一个扇区:
while ((掩码和1)==0)
{
掩码=掩码>> 1;
i++;
}
//擦除
// uint16_t stat0 = DisableInt();
uint32_t 扇区= FLASHPROG_FlashSecorStartAddr[i];
Debug_printf ("FLASHPROG_eraseSectors:擦除扇区0x%X\n"、扇区);
#if 0 //仅测试,假擦除
状态= Fapi_Status_Success;
其他
状态= Fapi_issueAppiCommandAppiAddress (Fapi_EraseSector、(uint32_t *)扇区);
fapi_flushPipeline();
if (status == Fapi_Status_Success)
{
while (fapi_checkFsmForReady()!= fapi_Status_FsmReady) asm (" NOP");
if (fapi_getFsmStatus ()=0)
{
//实际上不需要(如果 EALLOW 被正确设置)-无论如何只检查0x2000字...
Fapi_FlashStatusWordType oFlashStatusWord;
状态= Fapi_doBlankCheck (((uint32_t *)扇区、0x1000、&oFlashStatusWord);
if (status!= Fapi_Status_Success)//<<<此处失败
{
debug_printf ("FLASHPROG_eraseSectors:扇区0x%X 不为空、status=%i\n"、扇区、状态);
//status = Fapi_Status_Success;//仅测试、强制成功
}
}
}
#endif
// RestoreInt (stat0);
//完成此扇区
掩码=掩码>> 1;
i++;
}
//保留闪存泵的控制
FlashPumpSemaphoreRegs.PUMPREQUEST.ALL = IPC_PUMP_KEY | 0x0;
EDIS;
Tonyo、
我没有查看代码-但您确认 EALLOW 和 Pump 信标已被处理。 安全性。
您能否使用 C2000Ware 中的闪存 API 示例检查是否能够成功擦除扇区?
谢谢、此致。
Vamsi
是的、闪存 API 示例按预期运行。
CPU2正在运行 EtherCAT 程序、这是产品接收闪存更新数据的方式。
CPU1和 CPU2之间是否存在任何可能禁止擦除的交互?
Tonyo、
感谢您运行该示例。 这表明您的电压线路达到所需的电平。
您可能希望集中精力处理 CPU1和 CPU2使用的任何共享资源-可能存在一些争用。
您已经检查了闪存泵信号量、FLSEM、安全性 和 EALLOW。
时钟配置和 RAM 使用情况如何? 检查一个 CPU 在另一个 CPU 执行闪存擦除时是否改变了时钟配置。 或者、如果有 RAM 被其他 CPU 覆盖(但是、购买一个 CPU 只能根据所有权写入一个给定的共享 RAM)。
您说它以前工作过、最近停止工作-也许您可以对这两个版本进行比较。
谢谢、此致、
Vamsi
我从示例复制了代码以初始化闪存、电荷泵等、然后擦除块并将其放入程序-调用 Fapi_setActiveFlashBank()会产生错误504:无效的 Hclk 值、这毫无意义、因为时钟从未改变(始终以200MHz 运行)。
仍在尝试确定主错误 CPU2可能会造成什么...
Tonyo、
您传递给 Fapi_initiatizeAPI()的频率是多少?
您在初始化闪存例程中使用的等待状态配置是什么?
CPU2应用是否获取时钟信号量并配置任何内容?
谢谢、此致、
Vamsi
两个 CPU 都以200MHz 的频率运行。
在初始化闪存例程中、等待状态被设定为3。 将其设置为0xF 的最大值不会改变任何东西。
仍在处理 CPU2正在执行或正在执行的操作。
Tonyo、
现在、您可能希望避免 CPU2调试 CPU1上的擦除(因为您不需要 CPU2进行擦除)。
您是否在 Fapi_UserDefinedFuncations.c 中编辑了任何内容?
谢谢、此致、
Vamsi
Fapi_UserDefinedFuncations.c 中没有任何更改
发出擦除闪存的命令后、在严格循环中运行 CPU2 500ms 不会发生任何变化。
发出擦除闪存的命令后、使 CPU2怠速运行也不起作用。
Tonyo、
您是否可以进行调试调用? 我们总部位于德克萨斯州休斯顿。 请告诉我您方便的日期和时间。
谢谢、此致、
Vamsi
我在俄勒冈州、上午10点到中午、M-F 是最好的
太平洋时间上午10点至中午
Tonyo、
好的。 我们可以在本周五上午11点举行会议。 请给我发送一个朋友请求(在我的姓名上移动、您将看到"请求好友"按钮)。 收到友谊请求后、我将向您发送会议邀请。
在我们进行调试调用之前、请从您的项目中删除任何专有信息、并保留我们需要调试的闪存编程代码。
谢谢、此致、
Vamsi
好的、我发送了请求、谢谢!
我真正需要知道的是、CPU2正在采取哪些措施来防止 CPU1擦除/编程闪存。 在指令集手册、TRM 或闪存 API TRM 中、我看不到任何相关内容。
我缺少什么?
Tonyo、
TRM 和闪存 API 指南以及有关 CPU1和 CPU2之间泵信标共享的示例讨论/演示。 我已经提到了这个以及时钟信号量(连同其他调试提示)。 您确认 已检查所有内容、但未发现任何问题。
因此、我认为我可以为查看您的代码提供一些帮助、因此询问您是否可以进行调试调用。 您是否要在这篇帖子中讨论此问题而不是呼叫? 因为您再次发布了问题。 请澄清。
谢谢、此致、
Vamsi
我认为此勘误建议不适用于您: 低功耗模式:关闭闪存或保持最小器件活动
请查看以防万一。
在勘误表中搜索上述建议: https://www.ti.com/lit/pdf/sprz412
谢谢、此致、
Vamsi
感谢您提供勘误表链接、我同意此通报不适用。
但是、在 CPU2通知 CPU1开始擦除闪存之前、我确实向 CPU2添加了一些代码以获取、关闭并释放闪存泵。 这没有解决该问题、但它确实告诉我、CPU1尝试擦除闪存时、CPU2不会对闪存泵产生任何影响。
Tonyo、
是的、一旦泵与 CPU1配合使用、CPU2就无法阻止它擦除它的组。
您说您的应用程序在早期就可以正常运行、在进行一些更改后停止工作。 您是否专注于您所做的改变?
谢谢、此致、
Vamsi
我所做的就是将擦除/编程示例复制到当 CPU2通知 CPU1初始化闪存 API 时调用的例程中:
还在寻找。
我看到链接器.cmd 文件已更改、这会影响闪存的擦除/编程吗?
Tonyo、
我将能够在明天调试调用之前查看您的上述新消息。
是的、您需要确保 API 及其相关函数映射到闪存以进行加载、并映射 RAM 以进行运行。 此外、请确保您不会擦除闪存 API 映射的扇区。
谢谢、此致、
Vamsi
Tonyo、
在您的闪存 API 调用之前、我看不到 EALLOW。
您有一个函数,但之后,您调用了 其他函数,如 SeizeFlashPump()-这些函数调用 EDIS。 因此、您需要在调用闪存 API 函数之前包含 EALLOW。
谢谢、此致、
Vamsi
我直接从 FLASH_programming CPU01示例中复制了它、它工作正常。 此外、在每个 API 调用之前添加 EALLOW 也不起作用。
Tonyo、
请参阅下面的 C2000Ware 示例。 在 EALLOW 之后没有任何其他代码。
如果您需要我们的帮助来进一步进行调试、请向我们发送一个我们可以在此处显示的独立项目。
谢谢、此致、
Vamsi
Tonyo、
您对此有任何更新吗? 擦除成功吗?
谢谢、此致、
Vamsi
否-如果我运行示例、我可以擦除闪存并对其进行编程、但我的应用程序使用运行 ecat 的 CPU2启动代码、该代码确实可以正常工作、但现在无法正常工作。 我无法向您发送一个"独立项目"、将花费不可合理的时间来完成 ecat 堆栈。 我被骗了。
Tonyo、
不确定我还能提供什么帮助。 我问您是否可以进行调试呼叫、您离线通知我您只喜欢 E2E 通信。
您能否在闪存 API 擦除函数执行之前打开寄存器视图并检查 EALLOW 的值?
谢谢、此致、
Vamsi
谢谢、我将进行检查。 坦率地说,我没有期望得到太多帮助,因为这是一个非常奇怪的问题。 你已经尽力了。 如果您遇到任何描述禁用擦除的文档、请将其转发给我-我已经展示了该示例的工作原理、但有一些内容禁止擦除、我无法解释它是什么!
在 RAM 地址空间中、您可以放置和执行基于 RAM 的代码的位置是否存在任何限制? 似乎通过链接器脚本移动内容会使情况变得更糟
Tonyo、
此新问题是否与本帖子中的原始讨论相关? 如果没有、请打开一个新帖子、以便可以指派 RAM 专家来帮助您。
请注意:堆栈应该被放置在16位 RAM 地址 范围内。
谢谢、此致、
Vamsi
是的、此问题仍在处理中。 似乎有一个.stack 和一个 taskStackSection、这两个是否都限制在前64k 16位地址字?
Tonyo、
我知道.stack。 在16位范围内尝试这两种方法。
对于您的新问题、 最好启动一个新帖子、因为这是一个两个月的旧帖子。
谢谢、此致、
Vamsi