本帖最后由 Switcc 于 2018-3-14 17:40 编辑 $ y9 G3 b- C, m, s 上上周本人发帖询问stm32H7平台移植DP83848 PHY驱动的帖子,详见) N6 R9 u* M# K7 ^1 f; Z E https://www.stmcu.org.cn/module/forum/thread-614912-1-1.html, 按照回帖建议直接使用cube库里LAN8742里的驱动,然后对照不同PHY芯片寄存器查看,可以读到寄存器数据,但是网络一直没有调通,特别是gratuitous arp设备上线的广播都抓不到,更不谈能PING通设备了。 / R- q# v# C; \% T% [( q 经过长达两周的反复测试和问题排查,直接问题出在MPU和CACHE处理上。现分享使能MPU、CACHE和不使能MPU、CACHE两种模式配置说明: 一、使能MPU、CACHE情况 1、main.c中 HAL_Init()上加上MPU和CACHE配置 /* USER CODE BEGIN 1 */8 T8 C/ E" [/ i; n: e MPU_Config();% D7 ^2 ]* \* K( u9 A( ^: } CPU_CACHE_Enable(); /* USER CODE END 1 */8 b$ B2 d7 @. m' H ' g) N2 [: X! }( o+ w0 C* a- ~ /* Reset of all peripherals, Initializes the Flash interface and the Systick. */6 l e5 Q- Q7 E) C8 ~+ r0 K HAL_Init();5 C0 w. j: X" N8 D8 @0 N /* USER CODE BEGIN 4 */" C+ i& a( u( w /** * @brief Configure the MPU attributes * @param None * @retval None */" v5 f8 f( E$ o1 q static void MPU_Config(void) { MPU_Region_InitTypeDef MPU_InitStruct;9 L5 ?. T) N5 y8 b2 o$ p& h' w! l /* Disable the MPU */" _0 h- y5 X3 e& O; o HAL_MPU_Disable(); R. t. x6 z U /* Configure the MPU attributes as Device not cacheable for ETH DMA descriptors */2 c1 E/ L! }; a0 L% h. G' _ MPU_InitStruct.Enable = MPU_REGION_ENABLE;! k# o% [3 s$ d* w* R$ O* J. e MPU_InitStruct.BaseAddress = 0x30040000;7 \$ n1 N( h1 R! s% c; H% L MPU_InitStruct.Size = MPU_REGION_SIZE_256B; MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS;5 ]$ [- x* v. c3 S ^5 h MPU_InitStruct.IsBufferable = MPU_ACCESS_BUFFERABLE; MPU_InitStruct.IsCacheable = MPU_ACCESS_NOT_CACHEABLE;! v5 z! {* f4 Y! c+ p MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE; MPU_InitStruct.Number = MPU_REGION_NUMBER0; MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;& M* s! T& {/ l* {1 {' w- L MPU_InitStruct.SubRegionDisable = 0x00;" _: o+ r) Q& m- y; e! n2 k MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_ENABLE; 5 Z( A# r, M) G HAL_MPU_ConfigRegion(&MPU_InitStruct);( C, M* X4 P) B4 ~ V# V, K& S( H2 V2 B+ y# G /* Configure the MPU attributes as Cacheable write through for LwIP RAM heap which contains the Tx buffers */, L; s6 {+ I! x MPU_InitStruct.Enable = MPU_REGION_ENABLE;9 E% m9 ^- w* J+ }- W MPU_InitStruct.BaseAddress = 0x30044000; MPU_InitStruct.Size = MPU_REGION_SIZE_16KB; MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS; MPU_InitStruct.IsBufferable = MPU_ACCESS_NOT_BUFFERABLE; MPU_InitStruct.IsCacheable = MPU_ACCESS_CACHEABLE;0 D* r2 f5 R9 a2 q" s MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE;" y- `, c% S' g5 o K q MPU_InitStruct.Number = MPU_REGION_NUMBER1;6 E H" r3 h3 {( n z MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;. W* z' g; @8 ?1 V/ j2 { MPU_InitStruct.SubRegionDisable = 0x00; MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_ENABLE;: H5 y5 m& I1 M" o9 [ HAL_MPU_ConfigRegion(&MPU_InitStruct);$ O( ~. n+ Z- m% U) `5 g$ F ; Z$ I% ^# L3 X- S /* Enable the MPU */. Z5 X3 X6 Y# g( { HAL_MPU_Enable(MPU_PRIVILEGED_DEFAULT); }7 Z# }( @; T' K! W& d /**7 O% {9 n: b$ Z* B * @brief CPU L1-Cache enable. * @param None. J0 ~7 [" y ]) e( ?" u% n * @retval None */1 d' N' k, H5 J0 Q- o! n+ W: U static void CPU_CACHE_Enable(void) { /* Enable I-Cache */$ C: t! C6 a9 e$ p: l* L0 ?5 L9 N/ W SCB_EnableICache(); /* Enable D-Cache */* f I( w5 k3 E* V5 h SCB_EnableDCache(); } 2、main.c中时钟配置中加上一句 使能SRAM3时钟% }- O5 T# p# w; U /* Enable D2 domain SRAM3 Clock (0x30040000 AXI)*/ __HAL_RCC_D2SRAM3_CLK_ENABLE(); # f6 V% @5 O4 \( A1 l- z & j- c: x1 {( R 3、ethernetif.c中DMARxDscrTab、DMATxDscrTab地址分配,注意和MPU对比: J' K' N- @% L! ]2 p$ i8 b 8 l$ K/ r% Y" d0 ^0 Z #if defined ( __ICCARM__ ) /*!< IAR Compiler */ #pragma location=0x30040000. R- K% T: T; [) ] V8 r9 ^ ETH_DMADescTypeDef DMARxDscrTab[ETH_RX_DESC_CNT]; /* Ethernet Rx DMA Descriptors */! N/ x8 ~# G( H& I #pragma location=0x300400602 N* [2 m' P8 \5 [% [" ^ ETH_DMADescTypeDef DMATxDscrTab[ETH_TX_DESC_CNT]; /* Ethernet Tx DMA Descriptors */ #pragma location=0x30040200' u7 O* c1 K: s$ H9 }( v8 Z uint8_t Rx_Buff[ETH_RX_DESC_CNT][ETH_RX_BUFFER_SIZE]; /* Ethernet Receive Buffers */* E6 p' m9 z$ j8 d( V3 Y #elif defined ( __CC_ARM ) /* MDK ARM Compiler */7 k4 B( _3 [& K! a9 m' C! o % h+ S8 Q/ @- ?4 i7 n __attribute__((at(0x30040000))) ETH_DMADescTypeDef DMARxDscrTab[ETH_RX_DESC_CNT]; /* Ethernet Rx DMA Descriptors */ __attribute__((at(0x30040060))) ETH_DMADescTypeDef DMATxDscrTab[ETH_TX_DESC_CNT]; /* Ethernet Tx DMA Descriptors *// k) p( X- q. U8 x0 p+ A __attribute__((at(0x30040200))) uint8_t Rx_Buff[ETH_RX_DESC_CNT][ETH_RX_BUFFER_SIZE]; /* Ethernet Receive Buffer */$ H+ n# H; Q! ~ o, ?9 X3 h $ d; P3 n2 R. _* w #elif defined ( __GNUC__ ) /* GNU Compiler */ 1 o( a- ~* s8 [. m8 V7 b, ? . D, K% Z4 Z: W+ Q ETH_DMADescTypeDef DMARxDscrTab[ETH_RX_DESC_CNT] __attribute__((section(".RxDecripSection"))); /* Ethernet Rx DMA Descriptors */ ETH_DMADescTypeDef DMATxDscrTab[ETH_TX_DESC_CNT] __attribute__((section(".TxDecripSection"))); /* Ethernet Tx DMA Descriptors */ uint8_t Rx_Buff[ETH_RX_DESC_CNT][ETH_RX_BUFFER_SIZE] __attribute__((section(".RxArraySection"))); /* Ethernet Receive Buffers */7 I3 ?% c6 R7 N2 k 8 q+ N/ w2 r5 ^. D: o# c! \ #endif( A6 G/ I% K0 x3 \6 z : A/ E" F" a1 i7 p; B, { 5 ~' W+ B& I* r: k' l# v4 m4 [ 4、low_level_output中( Y$ A' T% W w5 g$ Y L& K, c/ }( S- z SCB_CleanInvalidateDCache();, G9 S% n m" J & E) _2 j( C. D- B8 |& Q4 h7 V HAL_ETH_Transmit(&heth, &TxConfig, 5); 5、low_level_input中) T2 D! y& E1 V) u8 A 4 Z* C9 P9 ?# I9 j2 x* b! ? c5 d /* Clean and Invalidate data cache */ SCB_CleanInvalidateDCache(); , \, ]+ S( L* E% K! J, d/ [ HAL_ETH_GetRxDataBuffer(&heth, &RxBuff);$ j8 C) ]7 p0 j1 O( O( D HAL_ETH_GetRxDataLength(&heth, &framelength);7 i$ L' O- I7 q/ | SCB_InvalidateDCache_by_Addr((uint32_t *)Rx_Buff, (ETH_RX_DESC_CNT*ETH_RX_BUFFER_SIZE)); s& J7 q4 _- ]$ j0 f * I4 ~: F$ Y& A5 ^5 Z8 [ 1 V& l# X2 F* S9 i ! P: _: w) B4 y. ]% ] 6、lwipopts.h中,注意和MPU对比 /* USER CODE BEGIN 1 */4 u6 a1 g/ s% A+ `0 t! S$ u* F #define LWIP_RAM_HEAP_POINTER (0x30044000) 7、ETH_RX_BUFFER_SIZE要一致9 j7 b2 ^% a# @5 L; V heth.Init.RxBuffLen = ETH_RX_BUFFER_SIZE; __attribute__((at(0x30040200))) uint8_t Rx_Buff[ETH_RX_DESC_CNT][ETH_RX_BUFFER_SIZE]; /* Ethernet Receive Buffer */' y& P& }' B7 l) K3 F' |* u : n% b: [, ?8 N7 C6 N SCB_InvalidateDCache_by_Addr((uint32_t *)Rx_Buff, (ETH_RX_DESC_CNT*ETH_RX_BUFFER_SIZE));+ {: B. y% l* Z# B; U% J; q p = pbuf_alloced_custom(PBUF_RAW, framelength, PBUF_POOL, &rx_pbuf[current_pbuf_idx], RxBuff.buffer, ETH_RX_BUFFER_SIZE); 5 n/ [" ]$ C% {4 w1 P 8、keil配置RAM如下,勾线IRAM2,不勾选IRAM16 r9 [$ U; V# q: H. | 见附件。 " C5 u1 M: Q4 y$ P, ~7 \ 二、不使能MPU、CACHE情况& c4 _' r5 g: H/ E' Y+ ^ 2 h8 p* N4 z7 P1 d: q3 a 上述1,4,5,6标红代码全部注释掉。# g/ O) }5 `9 L. |$ H 三、注意事项 1、网络相关管脚配置成高速,cube默认是低速( R* h$ x: f$ D8 e; [. r 2、可以先禁止MPU和cache,屏蔽掉相关代码,待网络测通后再开启MPU和cache,进行对应配置 3、H7目前官方库支持不到位,特别是有些examples完全没有经过验证,需特别注意/ V, C3 s$ L& z# f 4、使用MPU和cache时,多看看手册,弄懂机制避免入坑 0 H* _& q5 w L, H2 K4 k( S |
【经验分享】STM32_H7_ADC
STM32H7R/S高性能MCU:安全性,大存储和优异图显赋能更多应用创新
Stm32H7XX GCC下分散加载实现
【银杏科技ARM+FPGA双核心应用】STM32H7系列10——ADC
DIY-STM32H750核心板
[nucleo-H7A3ZI-Q]1-点亮一个皮皮灯
DIY-STM32H743核心板
【银杏科技ARM+FPGA双核心应用】STM32H7系列57——MDK_FLM
1月10日有奖直播 | 基于STM32 的CODESYS智能自动化解决方案
STM32的CAN FD位定时设置注意事项
在大数据量通信交互时,会造成TCP链接中断,抓包显示服务器端有RST,ACK异常,同时ping大包ping不通。经过调试分析,原因是定义的DMA描述定义和RX_buff不够,同时ETHIN的优先级较低导致Lwip内存访问异常。
修改方法:
1.ETH_RX_DESC_CNT 和 ETH_TX_DESC_CNT默认个数是4,根据通信负荷需要扩大,我这里分别扩大到16;
2.修改ETH_DMADescTypeDef
RX:0x30040000
TX:0x30040180
Rx_buff:0x30040400
3.修改MPU的配置
MPU_InitStruct.Enable = MPU_REGION_ENABLE;
MPU_InitStruct.BaseAddress = 0x30040000;
MPU_InitStruct.Size = MPU_REGION_SIZE_256B; //从256B 修改为 1K
MPU_InitStruct.AccessPermission = MPU_REGION_FULL_ACCESS;
MPU_InitStruct.IsBufferable = MPU_ACCESS_BUFFERABLE;
MPU_InitStruct.IsCacheable = MPU_ACCESS_NOT_CACHEABLE;
MPU_InitStruct.IsShareable = MPU_ACCESS_NOT_SHAREABLE;
MPU_InitStruct.Number = MPU_REGION_NUMBER0;
MPU_InitStruct.TypeExtField = MPU_TEX_LEVEL0;
MPU_InitStruct.SubRegionDisable = 0x00;
MPU_InitStruct.DisableExec = MPU_INSTRUCTION_ACCESS_ENABLE;
4.串口打印可能有影响,视情况关闭;
5.将ETHIN 和 Lwip的任务优先级提高
4 _0 u# o( u) [7 s
之前用的是F207+DP83848,很容易就调通了,这次换了H7之后,CubeMX里面配置完全不一样了,卡了2天,看到楼主发的注意事项,1个小时就调通了,非常感谢!
我再补充一点,在配置LWIP之前,需要先给PHY芯片一个硬复位,不然配置不成功,H7的RAM起始地址一定要是0x24000000,我用的是IAR,修改RAM起始地址的方法跟KEIL不太一样,ALT+F7打开“option”选项,然后选择“Linker”>"Config">"Edit">"Memory Regions"修改即可;
另外有点注意的就是 使用CubeMX生成的“ethernetif.c”里面,默认的heth.Init.RxBuffLen是1524,但是在"stm32h7xx_hal_eth.h"中,默认的ETH_MAX_PACKET_SIZE 大小是1528,这两个是不一样的,需要手动改成一样的数。
要是早两天看到你的帖子我就告诉你这个问题出在cache上了,我也正在调试H743的ETH,也是碰到了cache问题。。。不过楼主也是蛮厉害的。不知道楼主有测速没有?我现在遇到的问题是Rx速度不堪入目。( }1 i& O! U9 }, ~( R7 J
netio:
) u* m) N0 u P5 i. f7 ?( f0 M
楼主能加方式交流一下吗?) w9 g$ U+ I9 d5 W6 j: M, L9 V
# K9 S, o: Y0 ]4 k! L4 N1 [' i
我耽搁了两周啊,后面被搞得没脾气了
https://www.stmcu.org.cn/module/forum/thread-615031-1-1.html
你好,你的速度是多少?& v w( H: S+ M9 p, j/ N0 ]
815201002