技术标签: 笔记 STM32H7 recv出错
中位机使用TCP方式接收数据时可能出现数据错误,出错概率极高,大约接收300字节内必出。错误如下:
中位机使用ST厂商自带的HAL库,该源代码在关闭网络接收的DCache(数据缓存)功能时有bug,可能导致部分区域的DCache未被关闭,从而导致TCP接收时可能从不正确的数据来源区拷贝数据,从而出错。
HAL库版本号: STM32H7xx HAL V1.9.0
STM32CubeMX版本: 6.1.0
中位机MCU: STM32H743
LWIP版本: 2.1.2
1 思路
出于对网络通信可靠性的极度信任,首先怀疑自己收到数据后的解析与处理有问题。我司通信协议为自定义,较为繁杂,代码中有需要操作数据指针的地方,存在修改接收到数据的可能性。
验证
屏蔽掉数据解析与处理函数后测试,错误依旧,由此定位问题出在网络接收流程;
2 思路
本次使用的LWIP版本为2.1.2,而本人之前用过的成熟版本为1.4.1,虽说理论上LWIP应该不会存在这么大的坑,但不管怎样先试试。
验证
开启LWIP_DEBUG及相关调试宏,结果发现错误依旧,且LWIP协议栈一切正常,无任何警告输出;
3思路
有无可能是TCP接收存储区不够大、从而导致数据接收溢出?
验证
分析其底层网络接收机制,发现其接收机制为循环队列,队列容量为4,每块大小为1524字节。
4 思路
TCP接收顶层函数是一个Task,其优先级为HIGH,已然高于其它任何用户Task。考虑到本工程使用了LWIP,其内部会自行创建几个网络Task,有无可能是TCP接收Task优先级不够高、被其它线程抢占?
验证
1)修改TCP接收任务的优先级为最高(osPriorityRealtime),错误依旧;
2)增大TCP接收任务的堆栈,错误依旧;
5 思路
网上有同行说可能是CPU处理能力不够,每接收一包后sleep一下。
验证
修改后错误依旧;
6 思路
网络接收通常会使用DMA,且STM32H743芯片有1级DCache功能。有无可能是DCache未及时刷新导致的数据一致性问题?
验证
1)查找网络接收数组的分配位置,固定为0x30040200;
2)查找代码中对该存储区域的RAM属性设置,发现未禁止DCache,即:使用DCache;
为保证DMA与Cache不产生一致性的问题,STM32官方提供了一系列关闭或清空Cache的库函数。按个人经验,为保险起见,在底层接收函数中应该有规避一致性问题的动作。查询底层接收代码,果然有所发现:
按字面来看,应该是OK的。继续往里追查SCB_InvalidateDCache_by_Addr()函数,又有所发现:
其中SCB_InvalidateDCache_by_Addr()是ST官方提供的函数。
查数据手册得知,STM32H7平台的Cache操作是以Cache Line作为最小单位的,一个Cache Line是32字节。
正常情况下,该函数的第1个参数addr操作的地址应该要求32字节对齐,第2个参数dsize应该是32字节的整数倍。这样才能保证对Cache的操作是真正以Cache Line为单位。否则一旦传入的addr不按32字节对齐,则将出现问题。果断追查TCP接收循环队列的首地址,果然存在不对齐情况。手动修改之,经测试,完美通过!
反思
32字节对齐其实既可以在调用时执行,也可以放在SCB_InvalidateDCache_by_Addr()函数内执行。我个人倾向后者,毕竟调用者究竟是否理解该机制是不敢保证的。
一、选择优化的数据类型原则使用可以正确存储的最小数据类型小的数据类型占用更少的磁盘、内存和CPU缓存,并且处理时需要的CPU周期也更少选择简单的数据类型简单的数据类型通常需要更少的CPU周期,整数比字符操作代价更低尽量避免NULL通常情况下最好设置指定列为NOT NULL,除非真的需要存储NULL值NULL会使用更多的存储空间,再MYSQL中需要特殊处理当可为..._mysql schema 存储
目录早期 ConcurrentHashMap:Java 8 和之后的版本的ConcurrentHashMap:Java基础-10早期 ConcurrentHashMap:其实现是基于:分离锁,也就是将内部进行分段(Segment),里面则是 HashEntry 的数组,和 HashMap 类似,哈希相同的条目也是以链表形式存放。HashEntry 内部使用 volatile(禁用缓存) 的 value 字段来保证可见性,也利用了不可变对象的机制以改进利用 Unsafe 提供的底层能力_concurrenthashmap分析
报错信息:RuntimeError: Exception thrown in SimpleITK N4BiasFieldCorrectionImageFilter_Execute: c:\b\3.6-64\itk-prefix\include\itk-4.13\itkImageToImageFilter.hxx:241:itk::ERROR: SubtractImageFilter(000..._n4偏移场校正
1. 2009年09月01日,移动应用商场(Mobile Markets)之广东移动百合的视频、139邮箱、139社区……等免流量业务,结束动感地带品牌用户的内测,正式面向广东移动全品牌用户。(为免流奠定了基础)2. 2010年5月份,菠菜网的网友“我很在乎你”付费测试后,成功提取了MM视频栏目里的直播地址,制作成百合s60v3客户端的补丁,并低调的分享给了网友。3. 2010年5月份,免_免流发展历程
打开OEM -sql 监视页面,出现如下报错:java.sql.SQLException: ORA-31011: XML 语法分析失败ORA-19202: XML 处理LPX-00225: 结束元素标记 "sql" 与起始元素标记 "action" 不匹配Error at line 46376时出错ORA-06512: 在 "SYS.DBMS_SQLTUNE", line 15503ORA-065...
complex(real[,image])函数作用(1)创建一个值为 real + imag * j 的复数(2)转化一个字符串或数为复数如果第一个参数为字符串,则不需要指定第二个参数,否则会出错。字符串里可以是具体的浮点数,整数,复数,不能写成它们的运算式。但若参数为具体的数值,就可以写成他们的运算式。 具体如下注意事项:(1)第一个参数为字符串时:<1><3>..._complex()
@[TOC](这里写目录标题原因方法一方法二问题区: 原因这是因为c语言编译器是从上往下执行的,也就是说你必须要把使用的函数名放在main函数之前,编译器把你写的代码读进去,每看到一个函数,就记下他的名字方法一把调用的函数写到main函数前面;如方法二我教程上面说可以把函数头写到main函数前面,什么叫做函数头?void Cheer()//这个就是函数头若上面的有错误,请各位大佬指出,谢谢..._c2371
7-4 韩信点兵 (10 分)在中国数学史上,广泛流传着一个“韩信点兵”的故事:韩信是汉高祖刘邦手下的大将,他英勇善战,智谋超群,为汉朝建立了卓越的功劳。据说韩信的数学水平也非常高超,他在点兵的时候,为了知道有多少兵,同时又能保住军事机密,便让士兵排队报数:按从1至5报数,记下最末一个士兵报的数为1;再按从1至6报数,记下最末一个士兵报的数为5;再按从1至7报数,记下最末一个士兵报的数为4..._将学号设置为韩信数并运行,输出韩信数和结果
概要:以下内容是有关600796讲解首先我们可以通过终端窗口输入 "python" 命令来查看本地是否已经安装Python以及Python的安装版本的最新信息,希望阅读后对您有所帮助!大家都了解学精Python是进到云计算技术行业的基本,那麼在学习培训以前大家先来掌握下Python自然环境是如何搭建的。Python可运用于多种多样平台,包含大伙儿了解的Window,Linux 和 Mac OS X...
Docker容器开启IPv6_docker ipv6
1. 以ORACLE10g为例,举例说明更改SID名称的过程。假如数据库的SID叫testdb,现在改成orcl,有以下6个步骤: 1,停止所有的oracle服务 1.1oracle的相关服务都以oracle为前缀,有以下几个: OracleService OrcleOraHome92TNSListener OracleDBConsle OracleJobSchedul
本文转载,原文链接:http://my.oschina.net/huangyong/blog/1753630. 引言今天想跟大家分享一下我主要的 Java 开发工具,我一般是这样工作的:用 IDEA 写代码,用 Maven 管理 jar 包依赖与项目打包,用 Git 进行代码版本控制。关于这三款工具的安装与配置的过程,本文不作说明,有不太明白的朋友,可以给我留言,我会尽力解答。下面