将数据添加到闪存中的段如何会扰乱程序的时序?

发布于 2024-07-05 21:39:52 字数 569 浏览 10 评论 0原文

我有一个实时嵌入式应用程序,其主周期以 10KHz 运行。 它在配置为从闪存启动的 TI TMS320C 上运行。 我最近向源文件添加了一个初始化的数组,突然间时间就搞砸了(以一种太复杂的方式无法很好地解释 - 本质上串行端口写入不再按时完成。)与

此相关的事情令人困惑我:

  • 甚至没有访问新数据,只是声明一个初始化的数组。
  • 它取决于大小 - 仅当数组大于 40 个字时才会出现问题。
  • 我知道我没有溢出链接映射中的任何数据段。
  • 没有数据缓存,因此这不是由于破坏缓存一致性造成的。

关于简单地增加闪存中 .cinit 段的大小如何影响代码的时序有什么想法吗?

附加信息:
我认为代码可能已经移动,但它与数据分离得很好。 我通过内存映射验证了错误前后所有代码段都具有相同的地址。 我还验证了没有一个段是完整的 - 地图中唯一发生变化的地址是 .cinit 部分中的少数地址。 该部分包含用于初始化 ram 中变量的数据值(如我的数组)。 调用 main() 后不应再访问它。

I have a real-time embedded app with the major cycle running at 10KHz. It runs on a TI TMS320C configured to boot from flash. I recently added an initialized array to a source file, and all of a sudden the timing is screwed up (in a way too complex to explain well - essentially a serial port write is no longer completing on time.)

The things about this that baffle me:

  • I'm not even accessing the new data, just declaring an initialized array.
  • It is size dependant - the problem only appears if the array is >40 words.
  • I know I'm not overflowing any data segments in the link map.
  • There is no data caching, so it's not due to disrupting cache consistency.

Any ideas on how simply increasing the size of the .cinit segment in flash can affect the timing of your code?

Additional Info:
I considered that maybe the code had moved, but it is well-separated from the data. I verified through the memory map that all the code segements have the same addresses before and after the bug. I also verified that none of the segments are full - The only addresses that change in the map are a handful in the .cinit section. That section contains data values used to initialize variables in ram (like my array). It shouldn't ever be accessed after main() is called.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

十秒萌定你 2024-07-12 21:39:52

我怀疑您的数据/代码与底层媒体/内存之间的一致性发生了变化。 添加数据会更改堆中内存的位置(取决于内存模型),并且可能会使代码跨越闪存设备上的“页面”边界,从而导致以前不存在的延迟。

My suspicions would point to a change in alignment between your data/code and the underlying media/memory. Adding to your data would change the locations of memory in your heap (depending on the memory model) and might put your code across a 'page' boundary on the flash device causing latency which was not there before.

家住魔仙堡 2024-07-12 21:39:52

我会冒着风险,声称您在这里没有性能问题,而是某种表现为性能问题的内存损坏。 将数组添加到可执行文件中以更改内存图片。 所以我的猜测是,您的内存损坏大部分是无害的(即覆盖未使用的内存部分),并且将内存移动超过 40 个字节会导致内​​存损坏产生更大的问题。 哪一个是真题

I would risk my self and claim that you don't have a performance problem here, rather some kind of memory corruption that symptoms as a performance problem. Adding an array to your executable changing the memory picture. So my guess will be that you have a memory corruption that mostly harmless (i.e overwriting not used part of the memory) and shifting your memory more than 40 bytes cause the memory corruption to make a bigger problem. Which one is a real questions

一绘本一梦想 2024-07-12 21:39:52

也许新的静态分配数组将现有数据推入较慢的内存区域,导致对该数据的访问变慢?

Perhaps the new statically allocated array pushes existing data into slower memory regions, causing accesses to that data to be slower?

守护在此方 2024-07-12 21:39:52

如果数组是其地址空间块中的最后一个,问题是否会再次出现? 如果没有,请查看您的映射,尝试移动数组声明,以便将放置在其后面的内容一一移至其前面。 通过这种方式,您可以查明相关对象并开始找出移动它导致延迟的原因。

Does the problem recur if the array is the last thing in its chunk of address space? If not, looking in your map, try moving the array declaration so that, one by one, things placed after it are shuffled to be before it instead. This way you can pinpoint the relevant object and begin to work out why moving it causes the delay.

花之痕靓丽 2024-07-12 21:39:52

也可能是银行或页面冲突。 也许您有两个经常调用的例程(中断处理程序等),它们位于同一页面,现在分为两个页面。

Could be a bank or page conflict in as well. Maybe you have two routines that are called quite often (interrupt handlers or so) that have been at the same page and are now split up in two pages.

会发光的星星闪亮亮i 2024-07-12 21:39:52

初始化是否会覆盖另一段相邻的代码?
是否有任何使用该数组的结构或变量现在更大并且可能导致堆栈溢出?

Could the initialization be overwriting another adjacent piece of code?
Are there any structs or variables that use the array, that are now bigger and could cause a stackoverflow?

樱桃奶球 2024-07-12 21:39:52

经过一天多盯着痕迹和生成的程序集后,我想我已经弄清楚了。
根本原因问题被证明是一个设计问题,只有当启动串行端口写入的 ISR 与更高优先级的 ISR 发生冲突时,才会导致故障。 时间恰好表明,只需向一个循环添加一些额外的指令即可导致两个中断发生冲突。

所以问题就变成了:在闪存中存储而不是访问附加数据如何导致附加指令被执行?

看来答案与 Frosty 和 Frederico 的建议相关,但并不完全相同。 新数组确实移动了一些现有变量,但不会跨页边界或移动到较慢的区域(在此板上,所有区域的访问时间应相同)。 但它确实改变了一些经常访问的结构的偏移量,这导致优化器发出稍微不同的指令序列来访问它们。 一种数据对齐可能会导致单周期流水线停顿,而另一种则不会。 这几条指令的时间偏移足以暴露潜在的问题。

After more than a day staring at traces and generated assembly, I think I figured it out.
The root cause problem turned out to be an design issue that caused glitches only if the ISR that kicked off the serial port write collided with a higher priority one. The timing just happened to work out that it only took adding a few extra instructions to one loop to cause the two interrupts to collide.

So the question becomes: How does storing, but not accessing, additional data in flash memory cause additional instructions to be executed?

It appears that the answer is related to, but not quite the same as, the suggestions by Frosty and Frederico. The new array does move some existing variables, but not across page boundaries or to slower regions (on this board, access times should be the same for all regions) . But it does change the offsets of some frequently accessed structures, which causes the optimizer to issue slightly different instruction sequences for accessing them. One data alignment may cause a one cycle pipeline stall, where the other does not. And those few instructions shifted timing enough enough to expose the underlying problem.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文