comparison Common/Drivers/STM32F4xx_HAL_DRIVER_v120/Src/stm32f4xx_hal_eth.c @ 38:5f11787b4f42

include in ostc4 repository
author heinrichsweikamp
date Sat, 28 Apr 2018 11:52:34 +0200
parents
children
comparison
equal deleted inserted replaced
37:ccc45c0e1ea2 38:5f11787b4f42
1 /**
2 ******************************************************************************
3 * @file stm32f4xx_hal_eth.c
4 * @author MCD Application Team
5 * @version V1.2.0
6 * @date 26-December-2014
7 * @brief ETH HAL module driver.
8 * This file provides firmware functions to manage the following
9 * functionalities of the Ethernet (ETH) peripheral:
10 * + Initialization and de-initialization functions
11 * + IO operation functions
12 * + Peripheral Control functions
13 * + Peripheral State and Errors functions
14 *
15 @verbatim
16 ==============================================================================
17 ##### How to use this driver #####
18 ==============================================================================
19 [..]
20 (#)Declare a ETH_HandleTypeDef handle structure, for example:
21 ETH_HandleTypeDef heth;
22
23 (#)Fill parameters of Init structure in heth handle
24
25 (#)Call HAL_ETH_Init() API to initialize the Ethernet peripheral (MAC, DMA, ...)
26
27 (#)Initialize the ETH low level resources through the HAL_ETH_MspInit() API:
28 (##) Enable the Ethernet interface clock using
29 (+++) __HAL_RCC_ETHMAC_CLK_ENABLE();
30 (+++) __HAL_RCC_ETHMACTX_CLK_ENABLE();
31 (+++) __HAL_RCC_ETHMACRX_CLK_ENABLE();
32
33 (##) Initialize the related GPIO clocks
34 (##) Configure Ethernet pin-out
35 (##) Configure Ethernet NVIC interrupt (IT mode)
36
37 (#)Initialize Ethernet DMA Descriptors in chain mode and point to allocated buffers:
38 (##) HAL_ETH_DMATxDescListInit(); for Transmission process
39 (##) HAL_ETH_DMARxDescListInit(); for Reception process
40
41 (#)Enable MAC and DMA transmission and reception:
42 (##) HAL_ETH_Start();
43
44 (#)Prepare ETH DMA TX Descriptors and give the hand to ETH DMA to transfer
45 the frame to MAC TX FIFO:
46 (##) HAL_ETH_TransmitFrame();
47
48 (#)Poll for a received frame in ETH RX DMA Descriptors and get received
49 frame parameters
50 (##) HAL_ETH_GetReceivedFrame(); (should be called into an infinite loop)
51
52 (#) Get a received frame when an ETH RX interrupt occurs:
53 (##) HAL_ETH_GetReceivedFrame_IT(); (called in IT mode only)
54
55 (#) Communicate with external PHY device:
56 (##) Read a specific register from the PHY
57 HAL_ETH_ReadPHYRegister();
58 (##) Write data to a specific RHY register:
59 HAL_ETH_WritePHYRegister();
60
61 (#) Configure the Ethernet MAC after ETH peripheral initialization
62 HAL_ETH_ConfigMAC(); all MAC parameters should be filled.
63
64 (#) Configure the Ethernet DMA after ETH peripheral initialization
65 HAL_ETH_ConfigDMA(); all DMA parameters should be filled.
66
67 -@- The PTP protocol and the DMA descriptors ring mode are not supported
68 in this driver
69
70 @endverbatim
71 ******************************************************************************
72 * @attention
73 *
74 * <h2><center>&copy; COPYRIGHT(c) 2014 STMicroelectronics</center></h2>
75 *
76 * Redistribution and use in source and binary forms, with or without modification,
77 * are permitted provided that the following conditions are met:
78 * 1. Redistributions of source code must retain the above copyright notice,
79 * this list of conditions and the following disclaimer.
80 * 2. Redistributions in binary form must reproduce the above copyright notice,
81 * this list of conditions and the following disclaimer in the documentation
82 * and/or other materials provided with the distribution.
83 * 3. Neither the name of STMicroelectronics nor the names of its contributors
84 * may be used to endorse or promote products derived from this software
85 * without specific prior written permission.
86 *
87 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
88 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
89 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
90 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
91 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
92 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
93 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
94 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
95 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
96 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
97 *
98 ******************************************************************************
99 */
100
101 /* Includes ------------------------------------------------------------------*/
102 #include "stm32f4xx_hal.h"
103
104 /** @addtogroup STM32F4xx_HAL_Driver
105 * @{
106 */
107
108 /** @defgroup ETH ETH
109 * @brief ETH HAL module driver
110 * @{
111 */
112
113 #ifdef HAL_ETH_MODULE_ENABLED
114
115 #if defined(STM32F407xx) || defined(STM32F417xx) || defined(STM32F427xx) || defined(STM32F437xx) || defined(STM32F429xx) || defined(STM32F439xx)
116
117 /* Private typedef -----------------------------------------------------------*/
118 /* Private define ------------------------------------------------------------*/
119 /** @defgroup ETH_Private_Constants ETH Private Constants
120 * @{
121 */
122 #define LINKED_STATE_TIMEOUT_VALUE ((uint32_t)2000) /* 2000 ms */
123 #define AUTONEGO_COMPLETED_TIMEOUT_VALUE ((uint32_t)1000) /* 1000 ms */
124
125 /**
126 * @}
127 */
128 /* Private macro -------------------------------------------------------------*/
129 /* Private variables ---------------------------------------------------------*/
130 /* Private function prototypes -----------------------------------------------*/
131 /** @defgroup ETH_Private_Functions ETH Private Functions
132 * @{
133 */
134 static void ETH_MACDMAConfig(ETH_HandleTypeDef *heth, uint32_t err);
135 static void ETH_MACAddressConfig(ETH_HandleTypeDef *heth, uint32_t MacAddr, uint8_t *Addr);
136 static void ETH_MACReceptionEnable(ETH_HandleTypeDef *heth);
137 static void ETH_MACReceptionDisable(ETH_HandleTypeDef *heth);
138 static void ETH_MACTransmissionEnable(ETH_HandleTypeDef *heth);
139 static void ETH_MACTransmissionDisable(ETH_HandleTypeDef *heth);
140 static void ETH_DMATransmissionEnable(ETH_HandleTypeDef *heth);
141 static void ETH_DMATransmissionDisable(ETH_HandleTypeDef *heth);
142 static void ETH_DMAReceptionEnable(ETH_HandleTypeDef *heth);
143 static void ETH_DMAReceptionDisable(ETH_HandleTypeDef *heth);
144 static void ETH_FlushTransmitFIFO(ETH_HandleTypeDef *heth);
145
146 /**
147 * @}
148 */
149 /* Private functions ---------------------------------------------------------*/
150
151 /** @defgroup ETH_Exported_Functions ETH Exported Functions
152 * @{
153 */
154
155 /** @defgroup ETH_Exported_Functions_Group1 Initialization and de-initialization functions
156 * @brief Initialization and Configuration functions
157 *
158 @verbatim
159 ===============================================================================
160 ##### Initialization and de-initialization functions #####
161 ===============================================================================
162 [..] This section provides functions allowing to:
163 (+) Initialize and configure the Ethernet peripheral
164 (+) De-initialize the Ethernet peripheral
165
166 @endverbatim
167 * @{
168 */
169
170 /**
171 * @brief Initializes the Ethernet MAC and DMA according to default
172 * parameters.
173 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
174 * the configuration information for ETHERNET module
175 * @retval HAL status
176 */
177 HAL_StatusTypeDef HAL_ETH_Init(ETH_HandleTypeDef *heth)
178 {
179 uint32_t tmpreg = 0, phyreg = 0;
180 uint32_t hclk = 60000000;
181 uint32_t tickstart = 0;
182 uint32_t err = ETH_SUCCESS;
183
184 /* Check the ETH peripheral state */
185 if(heth == NULL)
186 {
187 return HAL_ERROR;
188 }
189
190 /* Check parameters */
191 assert_param(IS_ETH_AUTONEGOTIATION(heth->Init.AutoNegotiation));
192 assert_param(IS_ETH_RX_MODE(heth->Init.RxMode));
193 assert_param(IS_ETH_CHECKSUM_MODE(heth->Init.ChecksumMode));
194 assert_param(IS_ETH_MEDIA_INTERFACE(heth->Init.MediaInterface));
195
196 if(heth->State == HAL_ETH_STATE_RESET)
197 {
198 /* Init the low level hardware : GPIO, CLOCK, NVIC. */
199 HAL_ETH_MspInit(heth);
200 }
201
202 /* Enable SYSCFG Clock */
203 __HAL_RCC_SYSCFG_CLK_ENABLE();
204
205 /* Select MII or RMII Mode*/
206 SYSCFG->PMC &= ~(SYSCFG_PMC_MII_RMII_SEL);
207 SYSCFG->PMC |= (uint32_t)heth->Init.MediaInterface;
208
209 /* Ethernet Software reset */
210 /* Set the SWR bit: resets all MAC subsystem internal registers and logic */
211 /* After reset all the registers holds their respective reset values */
212 (heth->Instance)->DMABMR |= ETH_DMABMR_SR;
213
214 /* Wait for software reset */
215 while (((heth->Instance)->DMABMR & ETH_DMABMR_SR) != (uint32_t)RESET)
216 {
217 }
218
219 /*-------------------------------- MAC Initialization ----------------------*/
220 /* Get the ETHERNET MACMIIAR value */
221 tmpreg = (heth->Instance)->MACMIIAR;
222 /* Clear CSR Clock Range CR[2:0] bits */
223 tmpreg &= ETH_MACMIIAR_CR_MASK;
224
225 /* Get hclk frequency value */
226 hclk = HAL_RCC_GetHCLKFreq();
227
228 /* Set CR bits depending on hclk value */
229 if((hclk >= 20000000)&&(hclk < 35000000))
230 {
231 /* CSR Clock Range between 20-35 MHz */
232 tmpreg |= (uint32_t)ETH_MACMIIAR_CR_Div16;
233 }
234 else if((hclk >= 35000000)&&(hclk < 60000000))
235 {
236 /* CSR Clock Range between 35-60 MHz */
237 tmpreg |= (uint32_t)ETH_MACMIIAR_CR_Div26;
238 }
239 else if((hclk >= 60000000)&&(hclk < 100000000))
240 {
241 /* CSR Clock Range between 60-100 MHz */
242 tmpreg |= (uint32_t)ETH_MACMIIAR_CR_Div42;
243 }
244 else if((hclk >= 100000000)&&(hclk < 150000000))
245 {
246 /* CSR Clock Range between 100-150 MHz */
247 tmpreg |= (uint32_t)ETH_MACMIIAR_CR_Div62;
248 }
249 else /* ((hclk >= 150000000)&&(hclk <= 168000000)) */
250 {
251 /* CSR Clock Range between 150-168 MHz */
252 tmpreg |= (uint32_t)ETH_MACMIIAR_CR_Div102;
253 }
254
255 /* Write to ETHERNET MAC MIIAR: Configure the ETHERNET CSR Clock Range */
256 (heth->Instance)->MACMIIAR = (uint32_t)tmpreg;
257
258 /*-------------------- PHY initialization and configuration ----------------*/
259 /* Put the PHY in reset mode */
260 if((HAL_ETH_WritePHYRegister(heth, PHY_BCR, PHY_RESET)) != HAL_OK)
261 {
262 /* In case of write timeout */
263 err = ETH_ERROR;
264
265 /* Config MAC and DMA */
266 ETH_MACDMAConfig(heth, err);
267
268 /* Set the ETH peripheral state to READY */
269 heth->State = HAL_ETH_STATE_READY;
270
271 /* Return HAL_ERROR */
272 return HAL_ERROR;
273 }
274
275 /* Delay to assure PHY reset */
276 HAL_Delay(PHY_RESET_DELAY);
277
278 if((heth->Init).AutoNegotiation != ETH_AUTONEGOTIATION_DISABLE)
279 {
280 /* Get tick */
281 tickstart = HAL_GetTick();
282
283 /* We wait for linked status */
284 do
285 {
286 HAL_ETH_ReadPHYRegister(heth, PHY_BSR, &phyreg);
287
288 /* Check for the Timeout */
289 if((HAL_GetTick() - tickstart ) > LINKED_STATE_TIMEOUT_VALUE)
290 {
291 /* In case of write timeout */
292 err = ETH_ERROR;
293
294 /* Config MAC and DMA */
295 ETH_MACDMAConfig(heth, err);
296
297 heth->State= HAL_ETH_STATE_READY;
298
299 /* Process Unlocked */
300 __HAL_UNLOCK(heth);
301
302 return HAL_TIMEOUT;
303 }
304 } while (((phyreg & PHY_LINKED_STATUS) != PHY_LINKED_STATUS));
305
306
307 /* Enable Auto-Negotiation */
308 if((HAL_ETH_WritePHYRegister(heth, PHY_BCR, PHY_AUTONEGOTIATION)) != HAL_OK)
309 {
310 /* In case of write timeout */
311 err = ETH_ERROR;
312
313 /* Config MAC and DMA */
314 ETH_MACDMAConfig(heth, err);
315
316 /* Set the ETH peripheral state to READY */
317 heth->State = HAL_ETH_STATE_READY;
318
319 /* Return HAL_ERROR */
320 return HAL_ERROR;
321 }
322
323 /* Get tick */
324 tickstart = HAL_GetTick();
325
326 /* Wait until the auto-negotiation will be completed */
327 do
328 {
329 HAL_ETH_ReadPHYRegister(heth, PHY_BSR, &phyreg);
330
331 /* Check for the Timeout */
332 if((HAL_GetTick() - tickstart ) > AUTONEGO_COMPLETED_TIMEOUT_VALUE)
333 {
334 /* In case of write timeout */
335 err = ETH_ERROR;
336
337 /* Config MAC and DMA */
338 ETH_MACDMAConfig(heth, err);
339
340 heth->State= HAL_ETH_STATE_READY;
341
342 /* Process Unlocked */
343 __HAL_UNLOCK(heth);
344
345 return HAL_TIMEOUT;
346 }
347
348 } while (((phyreg & PHY_AUTONEGO_COMPLETE) != PHY_AUTONEGO_COMPLETE));
349
350 /* Read the result of the auto-negotiation */
351 if((HAL_ETH_ReadPHYRegister(heth, PHY_SR, &phyreg)) != HAL_OK)
352 {
353 /* In case of write timeout */
354 err = ETH_ERROR;
355
356 /* Config MAC and DMA */
357 ETH_MACDMAConfig(heth, err);
358
359 /* Set the ETH peripheral state to READY */
360 heth->State = HAL_ETH_STATE_READY;
361
362 /* Return HAL_ERROR */
363 return HAL_ERROR;
364 }
365
366 /* Configure the MAC with the Duplex Mode fixed by the auto-negotiation process */
367 if((phyreg & PHY_DUPLEX_STATUS) != (uint32_t)RESET)
368 {
369 /* Set Ethernet duplex mode to Full-duplex following the auto-negotiation */
370 (heth->Init).DuplexMode = ETH_MODE_FULLDUPLEX;
371 }
372 else
373 {
374 /* Set Ethernet duplex mode to Half-duplex following the auto-negotiation */
375 (heth->Init).DuplexMode = ETH_MODE_HALFDUPLEX;
376 }
377 /* Configure the MAC with the speed fixed by the auto-negotiation process */
378 if((phyreg & PHY_SPEED_STATUS) == PHY_SPEED_STATUS)
379 {
380 /* Set Ethernet speed to 10M following the auto-negotiation */
381 (heth->Init).Speed = ETH_SPEED_10M;
382 }
383 else
384 {
385 /* Set Ethernet speed to 100M following the auto-negotiation */
386 (heth->Init).Speed = ETH_SPEED_100M;
387 }
388 }
389 else /* AutoNegotiation Disable */
390 {
391 /* Check parameters */
392 assert_param(IS_ETH_SPEED(heth->Init.Speed));
393 assert_param(IS_ETH_DUPLEX_MODE(heth->Init.DuplexMode));
394
395 /* Set MAC Speed and Duplex Mode */
396 if(HAL_ETH_WritePHYRegister(heth, PHY_BCR, ((uint16_t)((heth->Init).DuplexMode >> 3) |
397 (uint16_t)((heth->Init).Speed >> 1))) != HAL_OK)
398 {
399 /* In case of write timeout */
400 err = ETH_ERROR;
401
402 /* Config MAC and DMA */
403 ETH_MACDMAConfig(heth, err);
404
405 /* Set the ETH peripheral state to READY */
406 heth->State = HAL_ETH_STATE_READY;
407
408 /* Return HAL_ERROR */
409 return HAL_ERROR;
410 }
411
412 /* Delay to assure PHY configuration */
413 HAL_Delay(PHY_CONFIG_DELAY);
414 }
415
416 /* Config MAC and DMA */
417 ETH_MACDMAConfig(heth, err);
418
419 /* Set ETH HAL State to Ready */
420 heth->State= HAL_ETH_STATE_READY;
421
422 /* Return function status */
423 return HAL_OK;
424 }
425
426 /**
427 * @brief De-Initializes the ETH peripheral.
428 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
429 * the configuration information for ETHERNET module
430 * @retval HAL status
431 */
432 HAL_StatusTypeDef HAL_ETH_DeInit(ETH_HandleTypeDef *heth)
433 {
434 /* Set the ETH peripheral state to BUSY */
435 heth->State = HAL_ETH_STATE_BUSY;
436
437 /* De-Init the low level hardware : GPIO, CLOCK, NVIC. */
438 HAL_ETH_MspDeInit(heth);
439
440 /* Set ETH HAL state to Disabled */
441 heth->State= HAL_ETH_STATE_RESET;
442
443 /* Release Lock */
444 __HAL_UNLOCK(heth);
445
446 /* Return function status */
447 return HAL_OK;
448 }
449
450 /**
451 * @brief Initializes the DMA Tx descriptors in chain mode.
452 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
453 * the configuration information for ETHERNET module
454 * @param DMATxDescTab: Pointer to the first Tx desc list
455 * @param TxBuff: Pointer to the first TxBuffer list
456 * @param TxBuffCount: Number of the used Tx desc in the list
457 * @retval HAL status
458 */
459 HAL_StatusTypeDef HAL_ETH_DMATxDescListInit(ETH_HandleTypeDef *heth, ETH_DMADescTypeDef *DMATxDescTab, uint8_t *TxBuff, uint32_t TxBuffCount)
460 {
461 uint32_t i = 0;
462 ETH_DMADescTypeDef *dmatxdesc;
463
464 /* Process Locked */
465 __HAL_LOCK(heth);
466
467 /* Set the ETH peripheral state to BUSY */
468 heth->State = HAL_ETH_STATE_BUSY;
469
470 /* Set the DMATxDescToSet pointer with the first one of the DMATxDescTab list */
471 heth->TxDesc = DMATxDescTab;
472
473 /* Fill each DMATxDesc descriptor with the right values */
474 for(i=0; i < TxBuffCount; i++)
475 {
476 /* Get the pointer on the ith member of the Tx Desc list */
477 dmatxdesc = DMATxDescTab + i;
478
479 /* Set Second Address Chained bit */
480 dmatxdesc->Status = ETH_DMATXDESC_TCH;
481
482 /* Set Buffer1 address pointer */
483 dmatxdesc->Buffer1Addr = (uint32_t)(&TxBuff[i*ETH_TX_BUF_SIZE]);
484
485 if ((heth->Init).ChecksumMode == ETH_CHECKSUM_BY_HARDWARE)
486 {
487 /* Set the DMA Tx descriptors checksum insertion */
488 dmatxdesc->Status |= ETH_DMATXDESC_CHECKSUMTCPUDPICMPFULL;
489 }
490
491 /* Initialize the next descriptor with the Next Descriptor Polling Enable */
492 if(i < (TxBuffCount-1))
493 {
494 /* Set next descriptor address register with next descriptor base address */
495 dmatxdesc->Buffer2NextDescAddr = (uint32_t)(DMATxDescTab+i+1);
496 }
497 else
498 {
499 /* For last descriptor, set next descriptor address register equal to the first descriptor base address */
500 dmatxdesc->Buffer2NextDescAddr = (uint32_t) DMATxDescTab;
501 }
502 }
503
504 /* Set Transmit Descriptor List Address Register */
505 (heth->Instance)->DMATDLAR = (uint32_t) DMATxDescTab;
506
507 /* Set ETH HAL State to Ready */
508 heth->State= HAL_ETH_STATE_READY;
509
510 /* Process Unlocked */
511 __HAL_UNLOCK(heth);
512
513 /* Return function status */
514 return HAL_OK;
515 }
516
517 /**
518 * @brief Initializes the DMA Rx descriptors in chain mode.
519 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
520 * the configuration information for ETHERNET module
521 * @param DMARxDescTab: Pointer to the first Rx desc list
522 * @param RxBuff: Pointer to the first RxBuffer list
523 * @param RxBuffCount: Number of the used Rx desc in the list
524 * @retval HAL status
525 */
526 HAL_StatusTypeDef HAL_ETH_DMARxDescListInit(ETH_HandleTypeDef *heth, ETH_DMADescTypeDef *DMARxDescTab, uint8_t *RxBuff, uint32_t RxBuffCount)
527 {
528 uint32_t i = 0;
529 ETH_DMADescTypeDef *DMARxDesc;
530
531 /* Process Locked */
532 __HAL_LOCK(heth);
533
534 /* Set the ETH peripheral state to BUSY */
535 heth->State = HAL_ETH_STATE_BUSY;
536
537 /* Set the Ethernet RxDesc pointer with the first one of the DMARxDescTab list */
538 heth->RxDesc = DMARxDescTab;
539
540 /* Fill each DMARxDesc descriptor with the right values */
541 for(i=0; i < RxBuffCount; i++)
542 {
543 /* Get the pointer on the ith member of the Rx Desc list */
544 DMARxDesc = DMARxDescTab+i;
545
546 /* Set Own bit of the Rx descriptor Status */
547 DMARxDesc->Status = ETH_DMARXDESC_OWN;
548
549 /* Set Buffer1 size and Second Address Chained bit */
550 DMARxDesc->ControlBufferSize = ETH_DMARXDESC_RCH | ETH_RX_BUF_SIZE;
551
552 /* Set Buffer1 address pointer */
553 DMARxDesc->Buffer1Addr = (uint32_t)(&RxBuff[i*ETH_RX_BUF_SIZE]);
554
555 if((heth->Init).RxMode == ETH_RXINTERRUPT_MODE)
556 {
557 /* Enable Ethernet DMA Rx Descriptor interrupt */
558 DMARxDesc->ControlBufferSize &= ~ETH_DMARXDESC_DIC;
559 }
560
561 /* Initialize the next descriptor with the Next Descriptor Polling Enable */
562 if(i < (RxBuffCount-1))
563 {
564 /* Set next descriptor address register with next descriptor base address */
565 DMARxDesc->Buffer2NextDescAddr = (uint32_t)(DMARxDescTab+i+1);
566 }
567 else
568 {
569 /* For last descriptor, set next descriptor address register equal to the first descriptor base address */
570 DMARxDesc->Buffer2NextDescAddr = (uint32_t)(DMARxDescTab);
571 }
572 }
573
574 /* Set Receive Descriptor List Address Register */
575 (heth->Instance)->DMARDLAR = (uint32_t) DMARxDescTab;
576
577 /* Set ETH HAL State to Ready */
578 heth->State= HAL_ETH_STATE_READY;
579
580 /* Process Unlocked */
581 __HAL_UNLOCK(heth);
582
583 /* Return function status */
584 return HAL_OK;
585 }
586
587 /**
588 * @brief Initializes the ETH MSP.
589 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
590 * the configuration information for ETHERNET module
591 * @retval None
592 */
593 __weak void HAL_ETH_MspInit(ETH_HandleTypeDef *heth)
594 {
595 /* NOTE : This function Should not be modified, when the callback is needed,
596 the HAL_ETH_MspInit could be implemented in the user file
597 */
598 }
599
600 /**
601 * @brief DeInitializes ETH MSP.
602 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
603 * the configuration information for ETHERNET module
604 * @retval None
605 */
606 __weak void HAL_ETH_MspDeInit(ETH_HandleTypeDef *heth)
607 {
608 /* NOTE : This function Should not be modified, when the callback is needed,
609 the HAL_ETH_MspDeInit could be implemented in the user file
610 */
611 }
612
613 /**
614 * @}
615 */
616
617 /** @defgroup ETH_Exported_Functions_Group2 IO operation functions
618 * @brief Data transfers functions
619 *
620 @verbatim
621 ==============================================================================
622 ##### IO operation functions #####
623 ==============================================================================
624 [..] This section provides functions allowing to:
625 (+) Transmit a frame
626 HAL_ETH_TransmitFrame();
627 (+) Receive a frame
628 HAL_ETH_GetReceivedFrame();
629 HAL_ETH_GetReceivedFrame_IT();
630 (+) Read from an External PHY register
631 HAL_ETH_ReadPHYRegister();
632 (+) Write to an External PHY register
633 HAL_ETH_WritePHYRegister();
634
635 @endverbatim
636
637 * @{
638 */
639
640 /**
641 * @brief Sends an Ethernet frame.
642 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
643 * the configuration information for ETHERNET module
644 * @param FrameLength: Amount of data to be sent
645 * @retval HAL status
646 */
647 HAL_StatusTypeDef HAL_ETH_TransmitFrame(ETH_HandleTypeDef *heth, uint32_t FrameLength)
648 {
649 uint32_t bufcount = 0, size = 0, i = 0;
650
651 /* Process Locked */
652 __HAL_LOCK(heth);
653
654 /* Set the ETH peripheral state to BUSY */
655 heth->State = HAL_ETH_STATE_BUSY;
656
657 if (FrameLength == 0)
658 {
659 /* Set ETH HAL state to READY */
660 heth->State = HAL_ETH_STATE_READY;
661
662 /* Process Unlocked */
663 __HAL_UNLOCK(heth);
664
665 return HAL_ERROR;
666 }
667
668 /* Check if the descriptor is owned by the ETHERNET DMA (when set) or CPU (when reset) */
669 if(((heth->TxDesc)->Status & ETH_DMATXDESC_OWN) != (uint32_t)RESET)
670 {
671 /* OWN bit set */
672 heth->State = HAL_ETH_STATE_BUSY_TX;
673
674 /* Process Unlocked */
675 __HAL_UNLOCK(heth);
676
677 return HAL_ERROR;
678 }
679
680 /* Get the number of needed Tx buffers for the current frame */
681 if (FrameLength > ETH_TX_BUF_SIZE)
682 {
683 bufcount = FrameLength/ETH_TX_BUF_SIZE;
684 if (FrameLength % ETH_TX_BUF_SIZE)
685 {
686 bufcount++;
687 }
688 }
689 else
690 {
691 bufcount = 1;
692 }
693 if (bufcount == 1)
694 {
695 /* Set LAST and FIRST segment */
696 heth->TxDesc->Status |=ETH_DMATXDESC_FS|ETH_DMATXDESC_LS;
697 /* Set frame size */
698 heth->TxDesc->ControlBufferSize = (FrameLength & ETH_DMATXDESC_TBS1);
699 /* Set Own bit of the Tx descriptor Status: gives the buffer back to ETHERNET DMA */
700 heth->TxDesc->Status |= ETH_DMATXDESC_OWN;
701 /* Point to next descriptor */
702 heth->TxDesc= (ETH_DMADescTypeDef *)(heth->TxDesc->Buffer2NextDescAddr);
703 }
704 else
705 {
706 for (i=0; i< bufcount; i++)
707 {
708 /* Clear FIRST and LAST segment bits */
709 heth->TxDesc->Status &= ~(ETH_DMATXDESC_FS | ETH_DMATXDESC_LS);
710
711 if (i == 0)
712 {
713 /* Setting the first segment bit */
714 heth->TxDesc->Status |= ETH_DMATXDESC_FS;
715 }
716
717 /* Program size */
718 heth->TxDesc->ControlBufferSize = (ETH_TX_BUF_SIZE & ETH_DMATXDESC_TBS1);
719
720 if (i == (bufcount-1))
721 {
722 /* Setting the last segment bit */
723 heth->TxDesc->Status |= ETH_DMATXDESC_LS;
724 size = FrameLength - (bufcount-1)*ETH_TX_BUF_SIZE;
725 heth->TxDesc->ControlBufferSize = (size & ETH_DMATXDESC_TBS1);
726 }
727
728 /* Set Own bit of the Tx descriptor Status: gives the buffer back to ETHERNET DMA */
729 heth->TxDesc->Status |= ETH_DMATXDESC_OWN;
730 /* point to next descriptor */
731 heth->TxDesc = (ETH_DMADescTypeDef *)(heth->TxDesc->Buffer2NextDescAddr);
732 }
733 }
734
735 /* When Tx Buffer unavailable flag is set: clear it and resume transmission */
736 if (((heth->Instance)->DMASR & ETH_DMASR_TBUS) != (uint32_t)RESET)
737 {
738 /* Clear TBUS ETHERNET DMA flag */
739 (heth->Instance)->DMASR = ETH_DMASR_TBUS;
740 /* Resume DMA transmission*/
741 (heth->Instance)->DMATPDR = 0;
742 }
743
744 /* Set ETH HAL State to Ready */
745 heth->State = HAL_ETH_STATE_READY;
746
747 /* Process Unlocked */
748 __HAL_UNLOCK(heth);
749
750 /* Return function status */
751 return HAL_OK;
752 }
753
754 /**
755 * @brief Checks for received frames.
756 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
757 * the configuration information for ETHERNET module
758 * @retval HAL status
759 */
760 HAL_StatusTypeDef HAL_ETH_GetReceivedFrame(ETH_HandleTypeDef *heth)
761 {
762 uint32_t framelength = 0;
763
764 /* Process Locked */
765 __HAL_LOCK(heth);
766
767 /* Check the ETH state to BUSY */
768 heth->State = HAL_ETH_STATE_BUSY;
769
770 /* Check if segment is not owned by DMA */
771 /* (((heth->RxDesc->Status & ETH_DMARXDESC_OWN) == (uint32_t)RESET) && ((heth->RxDesc->Status & ETH_DMARXDESC_LS) != (uint32_t)RESET)) */
772 if(((heth->RxDesc->Status & ETH_DMARXDESC_OWN) == (uint32_t)RESET))
773 {
774 /* Check if last segment */
775 if(((heth->RxDesc->Status & ETH_DMARXDESC_LS) != (uint32_t)RESET))
776 {
777 /* increment segment count */
778 (heth->RxFrameInfos).SegCount++;
779
780 /* Check if last segment is first segment: one segment contains the frame */
781 if ((heth->RxFrameInfos).SegCount == 1)
782 {
783 (heth->RxFrameInfos).FSRxDesc =heth->RxDesc;
784 }
785
786 heth->RxFrameInfos.LSRxDesc = heth->RxDesc;
787
788 /* Get the Frame Length of the received packet: substruct 4 bytes of the CRC */
789 framelength = (((heth->RxDesc)->Status & ETH_DMARXDESC_FL) >> ETH_DMARXDESC_FRAMELENGTHSHIFT) - 4;
790 heth->RxFrameInfos.length = framelength;
791
792 /* Get the address of the buffer start address */
793 heth->RxFrameInfos.buffer = ((heth->RxFrameInfos).FSRxDesc)->Buffer1Addr;
794 /* point to next descriptor */
795 heth->RxDesc = (ETH_DMADescTypeDef*) ((heth->RxDesc)->Buffer2NextDescAddr);
796
797 /* Set HAL State to Ready */
798 heth->State = HAL_ETH_STATE_READY;
799
800 /* Process Unlocked */
801 __HAL_UNLOCK(heth);
802
803 /* Return function status */
804 return HAL_OK;
805 }
806 /* Check if first segment */
807 else if((heth->RxDesc->Status & ETH_DMARXDESC_FS) != (uint32_t)RESET)
808 {
809 (heth->RxFrameInfos).FSRxDesc = heth->RxDesc;
810 (heth->RxFrameInfos).LSRxDesc = NULL;
811 (heth->RxFrameInfos).SegCount = 1;
812 /* Point to next descriptor */
813 heth->RxDesc = (ETH_DMADescTypeDef*) (heth->RxDesc->Buffer2NextDescAddr);
814 }
815 /* Check if intermediate segment */
816 else
817 {
818 (heth->RxFrameInfos).SegCount++;
819 /* Point to next descriptor */
820 heth->RxDesc = (ETH_DMADescTypeDef*) (heth->RxDesc->Buffer2NextDescAddr);
821 }
822 }
823
824 /* Set ETH HAL State to Ready */
825 heth->State = HAL_ETH_STATE_READY;
826
827 /* Process Unlocked */
828 __HAL_UNLOCK(heth);
829
830 /* Return function status */
831 return HAL_ERROR;
832 }
833
834 /**
835 * @brief Gets the Received frame in interrupt mode.
836 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
837 * the configuration information for ETHERNET module
838 * @retval HAL status
839 */
840 HAL_StatusTypeDef HAL_ETH_GetReceivedFrame_IT(ETH_HandleTypeDef *heth)
841 {
842 uint32_t descriptorscancounter = 0;
843
844 /* Process Locked */
845 __HAL_LOCK(heth);
846
847 /* Set ETH HAL State to BUSY */
848 heth->State = HAL_ETH_STATE_BUSY;
849
850 /* Scan descriptors owned by CPU */
851 while (((heth->RxDesc->Status & ETH_DMARXDESC_OWN) == (uint32_t)RESET) && (descriptorscancounter < ETH_RXBUFNB))
852 {
853 /* Just for security */
854 descriptorscancounter++;
855
856 /* Check if first segment in frame */
857 /* ((heth->RxDesc->Status & ETH_DMARXDESC_FS) != (uint32_t)RESET) && ((heth->RxDesc->Status & ETH_DMARXDESC_LS) == (uint32_t)RESET)) */
858 if((heth->RxDesc->Status & (ETH_DMARXDESC_FS | ETH_DMARXDESC_LS)) == (uint32_t)ETH_DMARXDESC_FS)
859 {
860 heth->RxFrameInfos.FSRxDesc = heth->RxDesc;
861 heth->RxFrameInfos.SegCount = 1;
862 /* Point to next descriptor */
863 heth->RxDesc = (ETH_DMADescTypeDef*) (heth->RxDesc->Buffer2NextDescAddr);
864 }
865 /* Check if intermediate segment */
866 /* ((heth->RxDesc->Status & ETH_DMARXDESC_LS) == (uint32_t)RESET)&& ((heth->RxDesc->Status & ETH_DMARXDESC_FS) == (uint32_t)RESET)) */
867 else if ((heth->RxDesc->Status & (ETH_DMARXDESC_LS | ETH_DMARXDESC_FS)) == (uint32_t)RESET)
868 {
869 /* Increment segment count */
870 (heth->RxFrameInfos.SegCount)++;
871 /* Point to next descriptor */
872 heth->RxDesc = (ETH_DMADescTypeDef*)(heth->RxDesc->Buffer2NextDescAddr);
873 }
874 /* Should be last segment */
875 else
876 {
877 /* Last segment */
878 heth->RxFrameInfos.LSRxDesc = heth->RxDesc;
879
880 /* Increment segment count */
881 (heth->RxFrameInfos.SegCount)++;
882
883 /* Check if last segment is first segment: one segment contains the frame */
884 if ((heth->RxFrameInfos.SegCount) == 1)
885 {
886 heth->RxFrameInfos.FSRxDesc = heth->RxDesc;
887 }
888
889 /* Get the Frame Length of the received packet: substruct 4 bytes of the CRC */
890 heth->RxFrameInfos.length = (((heth->RxDesc)->Status & ETH_DMARXDESC_FL) >> ETH_DMARXDESC_FRAMELENGTHSHIFT) - 4;
891
892 /* Get the address of the buffer start address */
893 heth->RxFrameInfos.buffer =((heth->RxFrameInfos).FSRxDesc)->Buffer1Addr;
894
895 /* Point to next descriptor */
896 heth->RxDesc = (ETH_DMADescTypeDef*) (heth->RxDesc->Buffer2NextDescAddr);
897
898 /* Set HAL State to Ready */
899 heth->State = HAL_ETH_STATE_READY;
900
901 /* Process Unlocked */
902 __HAL_UNLOCK(heth);
903
904 /* Return function status */
905 return HAL_OK;
906 }
907 }
908
909 /* Set HAL State to Ready */
910 heth->State = HAL_ETH_STATE_READY;
911
912 /* Process Unlocked */
913 __HAL_UNLOCK(heth);
914
915 /* Return function status */
916 return HAL_ERROR;
917 }
918
919 /**
920 * @brief This function handles ETH interrupt request.
921 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
922 * the configuration information for ETHERNET module
923 * @retval HAL status
924 */
925 void HAL_ETH_IRQHandler(ETH_HandleTypeDef *heth)
926 {
927 /* Frame received */
928 if (__HAL_ETH_DMA_GET_FLAG(heth, ETH_DMA_FLAG_R))
929 {
930 /* Receive complete callback */
931 HAL_ETH_RxCpltCallback(heth);
932
933 /* Clear the Eth DMA Rx IT pending bits */
934 __HAL_ETH_DMA_CLEAR_IT(heth, ETH_DMA_IT_R);
935
936 /* Set HAL State to Ready */
937 heth->State = HAL_ETH_STATE_READY;
938
939 /* Process Unlocked */
940 __HAL_UNLOCK(heth);
941
942 }
943 /* Frame transmitted */
944 else if (__HAL_ETH_DMA_GET_FLAG(heth, ETH_DMA_FLAG_T))
945 {
946 /* Transfer complete callback */
947 HAL_ETH_TxCpltCallback(heth);
948
949 /* Clear the Eth DMA Tx IT pending bits */
950 __HAL_ETH_DMA_CLEAR_IT(heth, ETH_DMA_IT_T);
951
952 /* Set HAL State to Ready */
953 heth->State = HAL_ETH_STATE_READY;
954
955 /* Process Unlocked */
956 __HAL_UNLOCK(heth);
957 }
958
959 /* Clear the interrupt flags */
960 __HAL_ETH_DMA_CLEAR_IT(heth, ETH_DMA_IT_NIS);
961
962 /* ETH DMA Error */
963 if(__HAL_ETH_DMA_GET_FLAG(heth, ETH_DMA_FLAG_AIS))
964 {
965 /* Ethernet Error callback */
966 HAL_ETH_ErrorCallback(heth);
967
968 /* Clear the interrupt flags */
969 __HAL_ETH_DMA_CLEAR_IT(heth, ETH_DMA_FLAG_AIS);
970
971 /* Set HAL State to Ready */
972 heth->State = HAL_ETH_STATE_READY;
973
974 /* Process Unlocked */
975 __HAL_UNLOCK(heth);
976 }
977 }
978
979 /**
980 * @brief Tx Transfer completed callbacks.
981 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
982 * the configuration information for ETHERNET module
983 * @retval None
984 */
985 __weak void HAL_ETH_TxCpltCallback(ETH_HandleTypeDef *heth)
986 {
987 /* NOTE : This function Should not be modified, when the callback is needed,
988 the HAL_ETH_TxCpltCallback could be implemented in the user file
989 */
990 }
991
992 /**
993 * @brief Rx Transfer completed callbacks.
994 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
995 * the configuration information for ETHERNET module
996 * @retval None
997 */
998 __weak void HAL_ETH_RxCpltCallback(ETH_HandleTypeDef *heth)
999 {
1000 /* NOTE : This function Should not be modified, when the callback is needed,
1001 the HAL_ETH_TxCpltCallback could be implemented in the user file
1002 */
1003 }
1004
1005 /**
1006 * @brief Ethernet transfer error callbacks
1007 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1008 * the configuration information for ETHERNET module
1009 * @retval None
1010 */
1011 __weak void HAL_ETH_ErrorCallback(ETH_HandleTypeDef *heth)
1012 {
1013 /* NOTE : This function Should not be modified, when the callback is needed,
1014 the HAL_ETH_TxCpltCallback could be implemented in the user file
1015 */
1016 }
1017
1018 /**
1019 * @brief Reads a PHY register
1020 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1021 * the configuration information for ETHERNET module
1022 * @param PHYReg: PHY register address, is the index of one of the 32 PHY register.
1023 * This parameter can be one of the following values:
1024 * PHY_BCR: Transceiver Basic Control Register,
1025 * PHY_BSR: Transceiver Basic Status Register.
1026 * More PHY register could be read depending on the used PHY
1027 * @param RegValue: PHY register value
1028 * @retval HAL status
1029 */
1030 HAL_StatusTypeDef HAL_ETH_ReadPHYRegister(ETH_HandleTypeDef *heth, uint16_t PHYReg, uint32_t *RegValue)
1031 {
1032 uint32_t tmpreg = 0;
1033 uint32_t tickstart = 0;
1034
1035 /* Check parameters */
1036 assert_param(IS_ETH_PHY_ADDRESS(heth->Init.PhyAddress));
1037
1038 /* Check the ETH peripheral state */
1039 if(heth->State == HAL_ETH_STATE_BUSY_RD)
1040 {
1041 return HAL_BUSY;
1042 }
1043 /* Set ETH HAL State to BUSY_RD */
1044 heth->State = HAL_ETH_STATE_BUSY_RD;
1045
1046 /* Get the ETHERNET MACMIIAR value */
1047 tmpreg = heth->Instance->MACMIIAR;
1048
1049 /* Keep only the CSR Clock Range CR[2:0] bits value */
1050 tmpreg &= ~ETH_MACMIIAR_CR_MASK;
1051
1052 /* Prepare the MII address register value */
1053 tmpreg |=(((uint32_t)heth->Init.PhyAddress << 11) & ETH_MACMIIAR_PA); /* Set the PHY device address */
1054 tmpreg |=(((uint32_t)PHYReg<<6) & ETH_MACMIIAR_MR); /* Set the PHY register address */
1055 tmpreg &= ~ETH_MACMIIAR_MW; /* Set the read mode */
1056 tmpreg |= ETH_MACMIIAR_MB; /* Set the MII Busy bit */
1057
1058 /* Write the result value into the MII Address register */
1059 heth->Instance->MACMIIAR = tmpreg;
1060
1061 /* Get tick */
1062 tickstart = HAL_GetTick();
1063
1064 /* Check for the Busy flag */
1065 while((tmpreg & ETH_MACMIIAR_MB) == ETH_MACMIIAR_MB)
1066 {
1067 /* Check for the Timeout */
1068 if((HAL_GetTick() - tickstart ) > PHY_READ_TO)
1069 {
1070 heth->State= HAL_ETH_STATE_READY;
1071
1072 /* Process Unlocked */
1073 __HAL_UNLOCK(heth);
1074
1075 return HAL_TIMEOUT;
1076 }
1077
1078 tmpreg = heth->Instance->MACMIIAR;
1079 }
1080
1081 /* Get MACMIIDR value */
1082 *RegValue = (uint16_t)(heth->Instance->MACMIIDR);
1083
1084 /* Set ETH HAL State to READY */
1085 heth->State = HAL_ETH_STATE_READY;
1086
1087 /* Return function status */
1088 return HAL_OK;
1089 }
1090
1091 /**
1092 * @brief Writes to a PHY register.
1093 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1094 * the configuration information for ETHERNET module
1095 * @param PHYReg: PHY register address, is the index of one of the 32 PHY register.
1096 * This parameter can be one of the following values:
1097 * PHY_BCR: Transceiver Control Register.
1098 * More PHY register could be written depending on the used PHY
1099 * @param RegValue: the value to write
1100 * @retval HAL status
1101 */
1102 HAL_StatusTypeDef HAL_ETH_WritePHYRegister(ETH_HandleTypeDef *heth, uint16_t PHYReg, uint32_t RegValue)
1103 {
1104 uint32_t tmpreg = 0;
1105 uint32_t tickstart = 0;
1106
1107 /* Check parameters */
1108 assert_param(IS_ETH_PHY_ADDRESS(heth->Init.PhyAddress));
1109
1110 /* Check the ETH peripheral state */
1111 if(heth->State == HAL_ETH_STATE_BUSY_WR)
1112 {
1113 return HAL_BUSY;
1114 }
1115 /* Set ETH HAL State to BUSY_WR */
1116 heth->State = HAL_ETH_STATE_BUSY_WR;
1117
1118 /* Get the ETHERNET MACMIIAR value */
1119 tmpreg = heth->Instance->MACMIIAR;
1120
1121 /* Keep only the CSR Clock Range CR[2:0] bits value */
1122 tmpreg &= ~ETH_MACMIIAR_CR_MASK;
1123
1124 /* Prepare the MII register address value */
1125 tmpreg |=(((uint32_t)heth->Init.PhyAddress<<11) & ETH_MACMIIAR_PA); /* Set the PHY device address */
1126 tmpreg |=(((uint32_t)PHYReg<<6) & ETH_MACMIIAR_MR); /* Set the PHY register address */
1127 tmpreg |= ETH_MACMIIAR_MW; /* Set the write mode */
1128 tmpreg |= ETH_MACMIIAR_MB; /* Set the MII Busy bit */
1129
1130 /* Give the value to the MII data register */
1131 heth->Instance->MACMIIDR = (uint16_t)RegValue;
1132
1133 /* Write the result value into the MII Address register */
1134 heth->Instance->MACMIIAR = tmpreg;
1135
1136 /* Get tick */
1137 tickstart = HAL_GetTick();
1138
1139 /* Check for the Busy flag */
1140 while((tmpreg & ETH_MACMIIAR_MB) == ETH_MACMIIAR_MB)
1141 {
1142 /* Check for the Timeout */
1143 if((HAL_GetTick() - tickstart ) > PHY_WRITE_TO)
1144 {
1145 heth->State= HAL_ETH_STATE_READY;
1146
1147 /* Process Unlocked */
1148 __HAL_UNLOCK(heth);
1149
1150 return HAL_TIMEOUT;
1151 }
1152
1153 tmpreg = heth->Instance->MACMIIAR;
1154 }
1155
1156 /* Set ETH HAL State to READY */
1157 heth->State = HAL_ETH_STATE_READY;
1158
1159 /* Return function status */
1160 return HAL_OK;
1161 }
1162
1163 /**
1164 * @}
1165 */
1166
1167 /** @defgroup ETH_Exported_Functions_Group3 Peripheral Control functions
1168 * @brief Peripheral Control functions
1169 *
1170 @verbatim
1171 ===============================================================================
1172 ##### Peripheral Control functions #####
1173 ===============================================================================
1174 [..] This section provides functions allowing to:
1175 (+) Enable MAC and DMA transmission and reception.
1176 HAL_ETH_Start();
1177 (+) Disable MAC and DMA transmission and reception.
1178 HAL_ETH_Stop();
1179 (+) Set the MAC configuration in runtime mode
1180 HAL_ETH_ConfigMAC();
1181 (+) Set the DMA configuration in runtime mode
1182 HAL_ETH_ConfigDMA();
1183
1184 @endverbatim
1185 * @{
1186 */
1187
1188 /**
1189 * @brief Enables Ethernet MAC and DMA reception/transmission
1190 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1191 * the configuration information for ETHERNET module
1192 * @retval HAL status
1193 */
1194 HAL_StatusTypeDef HAL_ETH_Start(ETH_HandleTypeDef *heth)
1195 {
1196 /* Process Locked */
1197 __HAL_LOCK(heth);
1198
1199 /* Set the ETH peripheral state to BUSY */
1200 heth->State = HAL_ETH_STATE_BUSY;
1201
1202 /* Enable transmit state machine of the MAC for transmission on the MII */
1203 ETH_MACTransmissionEnable(heth);
1204
1205 /* Enable receive state machine of the MAC for reception from the MII */
1206 ETH_MACReceptionEnable(heth);
1207
1208 /* Flush Transmit FIFO */
1209 ETH_FlushTransmitFIFO(heth);
1210
1211 /* Start DMA transmission */
1212 ETH_DMATransmissionEnable(heth);
1213
1214 /* Start DMA reception */
1215 ETH_DMAReceptionEnable(heth);
1216
1217 /* Set the ETH state to READY*/
1218 heth->State= HAL_ETH_STATE_READY;
1219
1220 /* Process Unlocked */
1221 __HAL_UNLOCK(heth);
1222
1223 /* Return function status */
1224 return HAL_OK;
1225 }
1226
1227 /**
1228 * @brief Stop Ethernet MAC and DMA reception/transmission
1229 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1230 * the configuration information for ETHERNET module
1231 * @retval HAL status
1232 */
1233 HAL_StatusTypeDef HAL_ETH_Stop(ETH_HandleTypeDef *heth)
1234 {
1235 /* Process Locked */
1236 __HAL_LOCK(heth);
1237
1238 /* Set the ETH peripheral state to BUSY */
1239 heth->State = HAL_ETH_STATE_BUSY;
1240
1241 /* Stop DMA transmission */
1242 ETH_DMATransmissionDisable(heth);
1243
1244 /* Stop DMA reception */
1245 ETH_DMAReceptionDisable(heth);
1246
1247 /* Disable receive state machine of the MAC for reception from the MII */
1248 ETH_MACReceptionDisable(heth);
1249
1250 /* Flush Transmit FIFO */
1251 ETH_FlushTransmitFIFO(heth);
1252
1253 /* Disable transmit state machine of the MAC for transmission on the MII */
1254 ETH_MACTransmissionDisable(heth);
1255
1256 /* Set the ETH state*/
1257 heth->State = HAL_ETH_STATE_READY;
1258
1259 /* Process Unlocked */
1260 __HAL_UNLOCK(heth);
1261
1262 /* Return function status */
1263 return HAL_OK;
1264 }
1265
1266 /**
1267 * @brief Set ETH MAC Configuration.
1268 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1269 * the configuration information for ETHERNET module
1270 * @param macconf: MAC Configuration structure
1271 * @retval HAL status
1272 */
1273 HAL_StatusTypeDef HAL_ETH_ConfigMAC(ETH_HandleTypeDef *heth, ETH_MACInitTypeDef *macconf)
1274 {
1275 uint32_t tmpreg = 0;
1276
1277 /* Process Locked */
1278 __HAL_LOCK(heth);
1279
1280 /* Set the ETH peripheral state to BUSY */
1281 heth->State= HAL_ETH_STATE_BUSY;
1282
1283 assert_param(IS_ETH_SPEED(heth->Init.Speed));
1284 assert_param(IS_ETH_DUPLEX_MODE(heth->Init.DuplexMode));
1285
1286 if (macconf != NULL)
1287 {
1288 /* Check the parameters */
1289 assert_param(IS_ETH_WATCHDOG(macconf->Watchdog));
1290 assert_param(IS_ETH_JABBER(macconf->Jabber));
1291 assert_param(IS_ETH_INTER_FRAME_GAP(macconf->InterFrameGap));
1292 assert_param(IS_ETH_CARRIER_SENSE(macconf->CarrierSense));
1293 assert_param(IS_ETH_RECEIVE_OWN(macconf->ReceiveOwn));
1294 assert_param(IS_ETH_LOOPBACK_MODE(macconf->LoopbackMode));
1295 assert_param(IS_ETH_CHECKSUM_OFFLOAD(macconf->ChecksumOffload));
1296 assert_param(IS_ETH_RETRY_TRANSMISSION(macconf->RetryTransmission));
1297 assert_param(IS_ETH_AUTOMATIC_PADCRC_STRIP(macconf->AutomaticPadCRCStrip));
1298 assert_param(IS_ETH_BACKOFF_LIMIT(macconf->BackOffLimit));
1299 assert_param(IS_ETH_DEFERRAL_CHECK(macconf->DeferralCheck));
1300 assert_param(IS_ETH_RECEIVE_ALL(macconf->ReceiveAll));
1301 assert_param(IS_ETH_SOURCE_ADDR_FILTER(macconf->SourceAddrFilter));
1302 assert_param(IS_ETH_CONTROL_FRAMES(macconf->PassControlFrames));
1303 assert_param(IS_ETH_BROADCAST_FRAMES_RECEPTION(macconf->BroadcastFramesReception));
1304 assert_param(IS_ETH_DESTINATION_ADDR_FILTER(macconf->DestinationAddrFilter));
1305 assert_param(IS_ETH_PROMISCUOUS_MODE(macconf->PromiscuousMode));
1306 assert_param(IS_ETH_MULTICAST_FRAMES_FILTER(macconf->MulticastFramesFilter));
1307 assert_param(IS_ETH_UNICAST_FRAMES_FILTER(macconf->UnicastFramesFilter));
1308 assert_param(IS_ETH_PAUSE_TIME(macconf->PauseTime));
1309 assert_param(IS_ETH_ZEROQUANTA_PAUSE(macconf->ZeroQuantaPause));
1310 assert_param(IS_ETH_PAUSE_LOW_THRESHOLD(macconf->PauseLowThreshold));
1311 assert_param(IS_ETH_UNICAST_PAUSE_FRAME_DETECT(macconf->UnicastPauseFrameDetect));
1312 assert_param(IS_ETH_RECEIVE_FLOWCONTROL(macconf->ReceiveFlowControl));
1313 assert_param(IS_ETH_TRANSMIT_FLOWCONTROL(macconf->TransmitFlowControl));
1314 assert_param(IS_ETH_VLAN_TAG_COMPARISON(macconf->VLANTagComparison));
1315 assert_param(IS_ETH_VLAN_TAG_IDENTIFIER(macconf->VLANTagIdentifier));
1316
1317 /*------------------------ ETHERNET MACCR Configuration --------------------*/
1318 /* Get the ETHERNET MACCR value */
1319 tmpreg = (heth->Instance)->MACCR;
1320 /* Clear WD, PCE, PS, TE and RE bits */
1321 tmpreg &= ETH_MACCR_CLEAR_MASK;
1322
1323 tmpreg |= (uint32_t)(macconf->Watchdog |
1324 macconf->Jabber |
1325 macconf->InterFrameGap |
1326 macconf->CarrierSense |
1327 (heth->Init).Speed |
1328 macconf->ReceiveOwn |
1329 macconf->LoopbackMode |
1330 (heth->Init).DuplexMode |
1331 macconf->ChecksumOffload |
1332 macconf->RetryTransmission |
1333 macconf->AutomaticPadCRCStrip |
1334 macconf->BackOffLimit |
1335 macconf->DeferralCheck);
1336
1337 /* Write to ETHERNET MACCR */
1338 (heth->Instance)->MACCR = (uint32_t)tmpreg;
1339
1340 /* Wait until the write operation will be taken into account :
1341 at least four TX_CLK/RX_CLK clock cycles */
1342 tmpreg = (heth->Instance)->MACCR;
1343 HAL_Delay(ETH_REG_WRITE_DELAY);
1344 (heth->Instance)->MACCR = tmpreg;
1345
1346 /*----------------------- ETHERNET MACFFR Configuration --------------------*/
1347 /* Write to ETHERNET MACFFR */
1348 (heth->Instance)->MACFFR = (uint32_t)(macconf->ReceiveAll |
1349 macconf->SourceAddrFilter |
1350 macconf->PassControlFrames |
1351 macconf->BroadcastFramesReception |
1352 macconf->DestinationAddrFilter |
1353 macconf->PromiscuousMode |
1354 macconf->MulticastFramesFilter |
1355 macconf->UnicastFramesFilter);
1356
1357 /* Wait until the write operation will be taken into account :
1358 at least four TX_CLK/RX_CLK clock cycles */
1359 tmpreg = (heth->Instance)->MACFFR;
1360 HAL_Delay(ETH_REG_WRITE_DELAY);
1361 (heth->Instance)->MACFFR = tmpreg;
1362
1363 /*--------------- ETHERNET MACHTHR and MACHTLR Configuration ---------------*/
1364 /* Write to ETHERNET MACHTHR */
1365 (heth->Instance)->MACHTHR = (uint32_t)macconf->HashTableHigh;
1366
1367 /* Write to ETHERNET MACHTLR */
1368 (heth->Instance)->MACHTLR = (uint32_t)macconf->HashTableLow;
1369 /*----------------------- ETHERNET MACFCR Configuration --------------------*/
1370
1371 /* Get the ETHERNET MACFCR value */
1372 tmpreg = (heth->Instance)->MACFCR;
1373 /* Clear xx bits */
1374 tmpreg &= ETH_MACFCR_CLEAR_MASK;
1375
1376 tmpreg |= (uint32_t)((macconf->PauseTime << 16) |
1377 macconf->ZeroQuantaPause |
1378 macconf->PauseLowThreshold |
1379 macconf->UnicastPauseFrameDetect |
1380 macconf->ReceiveFlowControl |
1381 macconf->TransmitFlowControl);
1382
1383 /* Write to ETHERNET MACFCR */
1384 (heth->Instance)->MACFCR = (uint32_t)tmpreg;
1385
1386 /* Wait until the write operation will be taken into account :
1387 at least four TX_CLK/RX_CLK clock cycles */
1388 tmpreg = (heth->Instance)->MACFCR;
1389 HAL_Delay(ETH_REG_WRITE_DELAY);
1390 (heth->Instance)->MACFCR = tmpreg;
1391
1392 /*----------------------- ETHERNET MACVLANTR Configuration -----------------*/
1393 (heth->Instance)->MACVLANTR = (uint32_t)(macconf->VLANTagComparison |
1394 macconf->VLANTagIdentifier);
1395
1396 /* Wait until the write operation will be taken into account :
1397 at least four TX_CLK/RX_CLK clock cycles */
1398 tmpreg = (heth->Instance)->MACVLANTR;
1399 HAL_Delay(ETH_REG_WRITE_DELAY);
1400 (heth->Instance)->MACVLANTR = tmpreg;
1401 }
1402 else /* macconf == NULL : here we just configure Speed and Duplex mode */
1403 {
1404 /*------------------------ ETHERNET MACCR Configuration --------------------*/
1405 /* Get the ETHERNET MACCR value */
1406 tmpreg = (heth->Instance)->MACCR;
1407
1408 /* Clear FES and DM bits */
1409 tmpreg &= ~((uint32_t)0x00004800);
1410
1411 tmpreg |= (uint32_t)(heth->Init.Speed | heth->Init.DuplexMode);
1412
1413 /* Write to ETHERNET MACCR */
1414 (heth->Instance)->MACCR = (uint32_t)tmpreg;
1415
1416 /* Wait until the write operation will be taken into account:
1417 at least four TX_CLK/RX_CLK clock cycles */
1418 tmpreg = (heth->Instance)->MACCR;
1419 HAL_Delay(ETH_REG_WRITE_DELAY);
1420 (heth->Instance)->MACCR = tmpreg;
1421 }
1422
1423 /* Set the ETH state to Ready */
1424 heth->State= HAL_ETH_STATE_READY;
1425
1426 /* Process Unlocked */
1427 __HAL_UNLOCK(heth);
1428
1429 /* Return function status */
1430 return HAL_OK;
1431 }
1432
1433 /**
1434 * @brief Sets ETH DMA Configuration.
1435 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1436 * the configuration information for ETHERNET module
1437 * @param dmaconf: DMA Configuration structure
1438 * @retval HAL status
1439 */
1440 HAL_StatusTypeDef HAL_ETH_ConfigDMA(ETH_HandleTypeDef *heth, ETH_DMAInitTypeDef *dmaconf)
1441 {
1442 uint32_t tmpreg = 0;
1443
1444 /* Process Locked */
1445 __HAL_LOCK(heth);
1446
1447 /* Set the ETH peripheral state to BUSY */
1448 heth->State= HAL_ETH_STATE_BUSY;
1449
1450 /* Check parameters */
1451 assert_param(IS_ETH_DROP_TCPIP_CHECKSUM_FRAME(dmaconf->DropTCPIPChecksumErrorFrame));
1452 assert_param(IS_ETH_RECEIVE_STORE_FORWARD(dmaconf->ReceiveStoreForward));
1453 assert_param(IS_ETH_FLUSH_RECEIVE_FRAME(dmaconf->FlushReceivedFrame));
1454 assert_param(IS_ETH_TRANSMIT_STORE_FORWARD(dmaconf->TransmitStoreForward));
1455 assert_param(IS_ETH_TRANSMIT_THRESHOLD_CONTROL(dmaconf->TransmitThresholdControl));
1456 assert_param(IS_ETH_FORWARD_ERROR_FRAMES(dmaconf->ForwardErrorFrames));
1457 assert_param(IS_ETH_FORWARD_UNDERSIZED_GOOD_FRAMES(dmaconf->ForwardUndersizedGoodFrames));
1458 assert_param(IS_ETH_RECEIVE_THRESHOLD_CONTROL(dmaconf->ReceiveThresholdControl));
1459 assert_param(IS_ETH_SECOND_FRAME_OPERATE(dmaconf->SecondFrameOperate));
1460 assert_param(IS_ETH_ADDRESS_ALIGNED_BEATS(dmaconf->AddressAlignedBeats));
1461 assert_param(IS_ETH_FIXED_BURST(dmaconf->FixedBurst));
1462 assert_param(IS_ETH_RXDMA_BURST_LENGTH(dmaconf->RxDMABurstLength));
1463 assert_param(IS_ETH_TXDMA_BURST_LENGTH(dmaconf->TxDMABurstLength));
1464 assert_param(IS_ETH_ENHANCED_DESCRIPTOR_FORMAT(dmaconf->EnhancedDescriptorFormat));
1465 assert_param(IS_ETH_DMA_DESC_SKIP_LENGTH(dmaconf->DescriptorSkipLength));
1466 assert_param(IS_ETH_DMA_ARBITRATION_ROUNDROBIN_RXTX(dmaconf->DMAArbitration));
1467
1468 /*----------------------- ETHERNET DMAOMR Configuration --------------------*/
1469 /* Get the ETHERNET DMAOMR value */
1470 tmpreg = (heth->Instance)->DMAOMR;
1471 /* Clear xx bits */
1472 tmpreg &= ETH_DMAOMR_CLEAR_MASK;
1473
1474 tmpreg |= (uint32_t)(dmaconf->DropTCPIPChecksumErrorFrame |
1475 dmaconf->ReceiveStoreForward |
1476 dmaconf->FlushReceivedFrame |
1477 dmaconf->TransmitStoreForward |
1478 dmaconf->TransmitThresholdControl |
1479 dmaconf->ForwardErrorFrames |
1480 dmaconf->ForwardUndersizedGoodFrames |
1481 dmaconf->ReceiveThresholdControl |
1482 dmaconf->SecondFrameOperate);
1483
1484 /* Write to ETHERNET DMAOMR */
1485 (heth->Instance)->DMAOMR = (uint32_t)tmpreg;
1486
1487 /* Wait until the write operation will be taken into account:
1488 at least four TX_CLK/RX_CLK clock cycles */
1489 tmpreg = (heth->Instance)->DMAOMR;
1490 HAL_Delay(ETH_REG_WRITE_DELAY);
1491 (heth->Instance)->DMAOMR = tmpreg;
1492
1493 /*----------------------- ETHERNET DMABMR Configuration --------------------*/
1494 (heth->Instance)->DMABMR = (uint32_t)(dmaconf->AddressAlignedBeats |
1495 dmaconf->FixedBurst |
1496 dmaconf->RxDMABurstLength | /* !! if 4xPBL is selected for Tx or Rx it is applied for the other */
1497 dmaconf->TxDMABurstLength |
1498 dmaconf->EnhancedDescriptorFormat |
1499 (dmaconf->DescriptorSkipLength << 2) |
1500 dmaconf->DMAArbitration |
1501 ETH_DMABMR_USP); /* Enable use of separate PBL for Rx and Tx */
1502
1503 /* Wait until the write operation will be taken into account:
1504 at least four TX_CLK/RX_CLK clock cycles */
1505 tmpreg = (heth->Instance)->DMABMR;
1506 HAL_Delay(ETH_REG_WRITE_DELAY);
1507 (heth->Instance)->DMABMR = tmpreg;
1508
1509 /* Set the ETH state to Ready */
1510 heth->State= HAL_ETH_STATE_READY;
1511
1512 /* Process Unlocked */
1513 __HAL_UNLOCK(heth);
1514
1515 /* Return function status */
1516 return HAL_OK;
1517 }
1518
1519 /**
1520 * @}
1521 */
1522
1523 /** @defgroup ETH_Exported_Functions_Group4 Peripheral State functions
1524 * @brief Peripheral State functions
1525 *
1526 @verbatim
1527 ===============================================================================
1528 ##### Peripheral State functions #####
1529 ===============================================================================
1530 [..]
1531 This subsection permits to get in run-time the status of the peripheral
1532 and the data flow.
1533 (+) Get the ETH handle state:
1534 HAL_ETH_GetState();
1535
1536
1537 @endverbatim
1538 * @{
1539 */
1540
1541 /**
1542 * @brief Return the ETH HAL state
1543 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1544 * the configuration information for ETHERNET module
1545 * @retval HAL state
1546 */
1547 HAL_ETH_StateTypeDef HAL_ETH_GetState(ETH_HandleTypeDef *heth)
1548 {
1549 /* Return ETH state */
1550 return heth->State;
1551 }
1552
1553 /**
1554 * @}
1555 */
1556
1557 /**
1558 * @}
1559 */
1560
1561 /** @addtogroup ETH_Private_Functions
1562 * @{
1563 */
1564
1565 /**
1566 * @brief Configures Ethernet MAC and DMA with default parameters.
1567 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1568 * the configuration information for ETHERNET module
1569 * @param err: Ethernet Init error
1570 * @retval HAL status
1571 */
1572 static void ETH_MACDMAConfig(ETH_HandleTypeDef *heth, uint32_t err)
1573 {
1574 ETH_MACInitTypeDef macinit;
1575 ETH_DMAInitTypeDef dmainit;
1576 uint32_t tmpreg = 0;
1577
1578 if (err != ETH_SUCCESS) /* Auto-negotiation failed */
1579 {
1580 /* Set Ethernet duplex mode to Full-duplex */
1581 (heth->Init).DuplexMode = ETH_MODE_FULLDUPLEX;
1582
1583 /* Set Ethernet speed to 100M */
1584 (heth->Init).Speed = ETH_SPEED_100M;
1585 }
1586
1587 /* Ethernet MAC default initialization **************************************/
1588 macinit.Watchdog = ETH_WATCHDOG_ENABLE;
1589 macinit.Jabber = ETH_JABBER_ENABLE;
1590 macinit.InterFrameGap = ETH_INTERFRAMEGAP_96BIT;
1591 macinit.CarrierSense = ETH_CARRIERSENCE_ENABLE;
1592 macinit.ReceiveOwn = ETH_RECEIVEOWN_ENABLE;
1593 macinit.LoopbackMode = ETH_LOOPBACKMODE_DISABLE;
1594 if(heth->Init.ChecksumMode == ETH_CHECKSUM_BY_HARDWARE)
1595 {
1596 macinit.ChecksumOffload = ETH_CHECKSUMOFFLAOD_ENABLE;
1597 }
1598 else
1599 {
1600 macinit.ChecksumOffload = ETH_CHECKSUMOFFLAOD_DISABLE;
1601 }
1602 macinit.RetryTransmission = ETH_RETRYTRANSMISSION_DISABLE;
1603 macinit.AutomaticPadCRCStrip = ETH_AUTOMATICPADCRCSTRIP_DISABLE;
1604 macinit.BackOffLimit = ETH_BACKOFFLIMIT_10;
1605 macinit.DeferralCheck = ETH_DEFFERRALCHECK_DISABLE;
1606 macinit.ReceiveAll = ETH_RECEIVEAll_DISABLE;
1607 macinit.SourceAddrFilter = ETH_SOURCEADDRFILTER_DISABLE;
1608 macinit.PassControlFrames = ETH_PASSCONTROLFRAMES_BLOCKALL;
1609 macinit.BroadcastFramesReception = ETH_BROADCASTFRAMESRECEPTION_ENABLE;
1610 macinit.DestinationAddrFilter = ETH_DESTINATIONADDRFILTER_NORMAL;
1611 macinit.PromiscuousMode = ETH_PROMISCUOUS_MODE_DISABLE;
1612 macinit.MulticastFramesFilter = ETH_MULTICASTFRAMESFILTER_PERFECT;
1613 macinit.UnicastFramesFilter = ETH_UNICASTFRAMESFILTER_PERFECT;
1614 macinit.HashTableHigh = 0x0;
1615 macinit.HashTableLow = 0x0;
1616 macinit.PauseTime = 0x0;
1617 macinit.ZeroQuantaPause = ETH_ZEROQUANTAPAUSE_DISABLE;
1618 macinit.PauseLowThreshold = ETH_PAUSELOWTHRESHOLD_MINUS4;
1619 macinit.UnicastPauseFrameDetect = ETH_UNICASTPAUSEFRAMEDETECT_DISABLE;
1620 macinit.ReceiveFlowControl = ETH_RECEIVEFLOWCONTROL_DISABLE;
1621 macinit.TransmitFlowControl = ETH_TRANSMITFLOWCONTROL_DISABLE;
1622 macinit.VLANTagComparison = ETH_VLANTAGCOMPARISON_16BIT;
1623 macinit.VLANTagIdentifier = 0x0;
1624
1625 /*------------------------ ETHERNET MACCR Configuration --------------------*/
1626 /* Get the ETHERNET MACCR value */
1627 tmpreg = (heth->Instance)->MACCR;
1628 /* Clear WD, PCE, PS, TE and RE bits */
1629 tmpreg &= ETH_MACCR_CLEAR_MASK;
1630 /* Set the WD bit according to ETH Watchdog value */
1631 /* Set the JD: bit according to ETH Jabber value */
1632 /* Set the IFG bit according to ETH InterFrameGap value */
1633 /* Set the DCRS bit according to ETH CarrierSense value */
1634 /* Set the FES bit according to ETH Speed value */
1635 /* Set the DO bit according to ETH ReceiveOwn value */
1636 /* Set the LM bit according to ETH LoopbackMode value */
1637 /* Set the DM bit according to ETH Mode value */
1638 /* Set the IPCO bit according to ETH ChecksumOffload value */
1639 /* Set the DR bit according to ETH RetryTransmission value */
1640 /* Set the ACS bit according to ETH AutomaticPadCRCStrip value */
1641 /* Set the BL bit according to ETH BackOffLimit value */
1642 /* Set the DC bit according to ETH DeferralCheck value */
1643 tmpreg |= (uint32_t)(macinit.Watchdog |
1644 macinit.Jabber |
1645 macinit.InterFrameGap |
1646 macinit.CarrierSense |
1647 (heth->Init).Speed |
1648 macinit.ReceiveOwn |
1649 macinit.LoopbackMode |
1650 (heth->Init).DuplexMode |
1651 macinit.ChecksumOffload |
1652 macinit.RetryTransmission |
1653 macinit.AutomaticPadCRCStrip |
1654 macinit.BackOffLimit |
1655 macinit.DeferralCheck);
1656
1657 /* Write to ETHERNET MACCR */
1658 (heth->Instance)->MACCR = (uint32_t)tmpreg;
1659
1660 /* Wait until the write operation will be taken into account:
1661 at least four TX_CLK/RX_CLK clock cycles */
1662 tmpreg = (heth->Instance)->MACCR;
1663 HAL_Delay(ETH_REG_WRITE_DELAY);
1664 (heth->Instance)->MACCR = tmpreg;
1665
1666 /*----------------------- ETHERNET MACFFR Configuration --------------------*/
1667 /* Set the RA bit according to ETH ReceiveAll value */
1668 /* Set the SAF and SAIF bits according to ETH SourceAddrFilter value */
1669 /* Set the PCF bit according to ETH PassControlFrames value */
1670 /* Set the DBF bit according to ETH BroadcastFramesReception value */
1671 /* Set the DAIF bit according to ETH DestinationAddrFilter value */
1672 /* Set the PR bit according to ETH PromiscuousMode value */
1673 /* Set the PM, HMC and HPF bits according to ETH MulticastFramesFilter value */
1674 /* Set the HUC and HPF bits according to ETH UnicastFramesFilter value */
1675 /* Write to ETHERNET MACFFR */
1676 (heth->Instance)->MACFFR = (uint32_t)(macinit.ReceiveAll |
1677 macinit.SourceAddrFilter |
1678 macinit.PassControlFrames |
1679 macinit.BroadcastFramesReception |
1680 macinit.DestinationAddrFilter |
1681 macinit.PromiscuousMode |
1682 macinit.MulticastFramesFilter |
1683 macinit.UnicastFramesFilter);
1684
1685 /* Wait until the write operation will be taken into account:
1686 at least four TX_CLK/RX_CLK clock cycles */
1687 tmpreg = (heth->Instance)->MACFFR;
1688 HAL_Delay(ETH_REG_WRITE_DELAY);
1689 (heth->Instance)->MACFFR = tmpreg;
1690
1691 /*--------------- ETHERNET MACHTHR and MACHTLR Configuration --------------*/
1692 /* Write to ETHERNET MACHTHR */
1693 (heth->Instance)->MACHTHR = (uint32_t)macinit.HashTableHigh;
1694
1695 /* Write to ETHERNET MACHTLR */
1696 (heth->Instance)->MACHTLR = (uint32_t)macinit.HashTableLow;
1697 /*----------------------- ETHERNET MACFCR Configuration -------------------*/
1698
1699 /* Get the ETHERNET MACFCR value */
1700 tmpreg = (heth->Instance)->MACFCR;
1701 /* Clear xx bits */
1702 tmpreg &= ETH_MACFCR_CLEAR_MASK;
1703
1704 /* Set the PT bit according to ETH PauseTime value */
1705 /* Set the DZPQ bit according to ETH ZeroQuantaPause value */
1706 /* Set the PLT bit according to ETH PauseLowThreshold value */
1707 /* Set the UP bit according to ETH UnicastPauseFrameDetect value */
1708 /* Set the RFE bit according to ETH ReceiveFlowControl value */
1709 /* Set the TFE bit according to ETH TransmitFlowControl value */
1710 tmpreg |= (uint32_t)((macinit.PauseTime << 16) |
1711 macinit.ZeroQuantaPause |
1712 macinit.PauseLowThreshold |
1713 macinit.UnicastPauseFrameDetect |
1714 macinit.ReceiveFlowControl |
1715 macinit.TransmitFlowControl);
1716
1717 /* Write to ETHERNET MACFCR */
1718 (heth->Instance)->MACFCR = (uint32_t)tmpreg;
1719
1720 /* Wait until the write operation will be taken into account:
1721 at least four TX_CLK/RX_CLK clock cycles */
1722 tmpreg = (heth->Instance)->MACFCR;
1723 HAL_Delay(ETH_REG_WRITE_DELAY);
1724 (heth->Instance)->MACFCR = tmpreg;
1725
1726 /*----------------------- ETHERNET MACVLANTR Configuration ----------------*/
1727 /* Set the ETV bit according to ETH VLANTagComparison value */
1728 /* Set the VL bit according to ETH VLANTagIdentifier value */
1729 (heth->Instance)->MACVLANTR = (uint32_t)(macinit.VLANTagComparison |
1730 macinit.VLANTagIdentifier);
1731
1732 /* Wait until the write operation will be taken into account:
1733 at least four TX_CLK/RX_CLK clock cycles */
1734 tmpreg = (heth->Instance)->MACVLANTR;
1735 HAL_Delay(ETH_REG_WRITE_DELAY);
1736 (heth->Instance)->MACVLANTR = tmpreg;
1737
1738 /* Ethernet DMA default initialization ************************************/
1739 dmainit.DropTCPIPChecksumErrorFrame = ETH_DROPTCPIPCHECKSUMERRORFRAME_ENABLE;
1740 dmainit.ReceiveStoreForward = ETH_RECEIVESTOREFORWARD_ENABLE;
1741 dmainit.FlushReceivedFrame = ETH_FLUSHRECEIVEDFRAME_ENABLE;
1742 dmainit.TransmitStoreForward = ETH_TRANSMITSTOREFORWARD_ENABLE;
1743 dmainit.TransmitThresholdControl = ETH_TRANSMITTHRESHOLDCONTROL_64BYTES;
1744 dmainit.ForwardErrorFrames = ETH_FORWARDERRORFRAMES_DISABLE;
1745 dmainit.ForwardUndersizedGoodFrames = ETH_FORWARDUNDERSIZEDGOODFRAMES_DISABLE;
1746 dmainit.ReceiveThresholdControl = ETH_RECEIVEDTHRESHOLDCONTROL_64BYTES;
1747 dmainit.SecondFrameOperate = ETH_SECONDFRAMEOPERARTE_ENABLE;
1748 dmainit.AddressAlignedBeats = ETH_ADDRESSALIGNEDBEATS_ENABLE;
1749 dmainit.FixedBurst = ETH_FIXEDBURST_ENABLE;
1750 dmainit.RxDMABurstLength = ETH_RXDMABURSTLENGTH_32BEAT;
1751 dmainit.TxDMABurstLength = ETH_TXDMABURSTLENGTH_32BEAT;
1752 dmainit.EnhancedDescriptorFormat = ETH_DMAENHANCEDDESCRIPTOR_ENABLE;
1753 dmainit.DescriptorSkipLength = 0x0;
1754 dmainit.DMAArbitration = ETH_DMAARBITRATION_ROUNDROBIN_RXTX_1_1;
1755
1756 /* Get the ETHERNET DMAOMR value */
1757 tmpreg = (heth->Instance)->DMAOMR;
1758 /* Clear xx bits */
1759 tmpreg &= ETH_DMAOMR_CLEAR_MASK;
1760
1761 /* Set the DT bit according to ETH DropTCPIPChecksumErrorFrame value */
1762 /* Set the RSF bit according to ETH ReceiveStoreForward value */
1763 /* Set the DFF bit according to ETH FlushReceivedFrame value */
1764 /* Set the TSF bit according to ETH TransmitStoreForward value */
1765 /* Set the TTC bit according to ETH TransmitThresholdControl value */
1766 /* Set the FEF bit according to ETH ForwardErrorFrames value */
1767 /* Set the FUF bit according to ETH ForwardUndersizedGoodFrames value */
1768 /* Set the RTC bit according to ETH ReceiveThresholdControl value */
1769 /* Set the OSF bit according to ETH SecondFrameOperate value */
1770 tmpreg |= (uint32_t)(dmainit.DropTCPIPChecksumErrorFrame |
1771 dmainit.ReceiveStoreForward |
1772 dmainit.FlushReceivedFrame |
1773 dmainit.TransmitStoreForward |
1774 dmainit.TransmitThresholdControl |
1775 dmainit.ForwardErrorFrames |
1776 dmainit.ForwardUndersizedGoodFrames |
1777 dmainit.ReceiveThresholdControl |
1778 dmainit.SecondFrameOperate);
1779
1780 /* Write to ETHERNET DMAOMR */
1781 (heth->Instance)->DMAOMR = (uint32_t)tmpreg;
1782
1783 /* Wait until the write operation will be taken into account:
1784 at least four TX_CLK/RX_CLK clock cycles */
1785 tmpreg = (heth->Instance)->DMAOMR;
1786 HAL_Delay(ETH_REG_WRITE_DELAY);
1787 (heth->Instance)->DMAOMR = tmpreg;
1788
1789 /*----------------------- ETHERNET DMABMR Configuration ------------------*/
1790 /* Set the AAL bit according to ETH AddressAlignedBeats value */
1791 /* Set the FB bit according to ETH FixedBurst value */
1792 /* Set the RPBL and 4*PBL bits according to ETH RxDMABurstLength value */
1793 /* Set the PBL and 4*PBL bits according to ETH TxDMABurstLength value */
1794 /* Set the Enhanced DMA descriptors bit according to ETH EnhancedDescriptorFormat value*/
1795 /* Set the DSL bit according to ETH DesciptorSkipLength value */
1796 /* Set the PR and DA bits according to ETH DMAArbitration value */
1797 (heth->Instance)->DMABMR = (uint32_t)(dmainit.AddressAlignedBeats |
1798 dmainit.FixedBurst |
1799 dmainit.RxDMABurstLength | /* !! if 4xPBL is selected for Tx or Rx it is applied for the other */
1800 dmainit.TxDMABurstLength |
1801 dmainit.EnhancedDescriptorFormat |
1802 (dmainit.DescriptorSkipLength << 2) |
1803 dmainit.DMAArbitration |
1804 ETH_DMABMR_USP); /* Enable use of separate PBL for Rx and Tx */
1805
1806 /* Wait until the write operation will be taken into account:
1807 at least four TX_CLK/RX_CLK clock cycles */
1808 tmpreg = (heth->Instance)->DMABMR;
1809 HAL_Delay(ETH_REG_WRITE_DELAY);
1810 (heth->Instance)->DMABMR = tmpreg;
1811
1812 if((heth->Init).RxMode == ETH_RXINTERRUPT_MODE)
1813 {
1814 /* Enable the Ethernet Rx Interrupt */
1815 __HAL_ETH_DMA_ENABLE_IT((heth), ETH_DMA_IT_NIS | ETH_DMA_IT_R);
1816 }
1817
1818 /* Initialize MAC address in ethernet MAC */
1819 ETH_MACAddressConfig(heth, ETH_MAC_ADDRESS0, heth->Init.MACAddr);
1820 }
1821
1822 /**
1823 * @brief Configures the selected MAC address.
1824 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1825 * the configuration information for ETHERNET module
1826 * @param MacAddr: The MAC address to configure
1827 * This parameter can be one of the following values:
1828 * @arg ETH_MAC_Address0: MAC Address0
1829 * @arg ETH_MAC_Address1: MAC Address1
1830 * @arg ETH_MAC_Address2: MAC Address2
1831 * @arg ETH_MAC_Address3: MAC Address3
1832 * @param Addr: Pointer to MAC address buffer data (6 bytes)
1833 * @retval HAL status
1834 */
1835 static void ETH_MACAddressConfig(ETH_HandleTypeDef *heth, uint32_t MacAddr, uint8_t *Addr)
1836 {
1837 uint32_t tmpreg;
1838
1839 /* Check the parameters */
1840 assert_param(IS_ETH_MAC_ADDRESS0123(MacAddr));
1841
1842 /* Calculate the selected MAC address high register */
1843 tmpreg = ((uint32_t)Addr[5] << 8) | (uint32_t)Addr[4];
1844 /* Load the selected MAC address high register */
1845 (*(__IO uint32_t *)((uint32_t)(ETH_MAC_ADDR_HBASE + MacAddr))) = tmpreg;
1846 /* Calculate the selected MAC address low register */
1847 tmpreg = ((uint32_t)Addr[3] << 24) | ((uint32_t)Addr[2] << 16) | ((uint32_t)Addr[1] << 8) | Addr[0];
1848
1849 /* Load the selected MAC address low register */
1850 (*(__IO uint32_t *)((uint32_t)(ETH_MAC_ADDR_LBASE + MacAddr))) = tmpreg;
1851 }
1852
1853 /**
1854 * @brief Enables the MAC transmission.
1855 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1856 * the configuration information for ETHERNET module
1857 * @retval None
1858 */
1859 static void ETH_MACTransmissionEnable(ETH_HandleTypeDef *heth)
1860 {
1861 __IO uint32_t tmpreg = 0;
1862
1863 /* Enable the MAC transmission */
1864 (heth->Instance)->MACCR |= ETH_MACCR_TE;
1865
1866 /* Wait until the write operation will be taken into account:
1867 at least four TX_CLK/RX_CLK clock cycles */
1868 tmpreg = (heth->Instance)->MACCR;
1869 HAL_Delay(ETH_REG_WRITE_DELAY);
1870 (heth->Instance)->MACCR = tmpreg;
1871 }
1872
1873 /**
1874 * @brief Disables the MAC transmission.
1875 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1876 * the configuration information for ETHERNET module
1877 * @retval None
1878 */
1879 static void ETH_MACTransmissionDisable(ETH_HandleTypeDef *heth)
1880 {
1881 __IO uint32_t tmpreg = 0;
1882
1883 /* Disable the MAC transmission */
1884 (heth->Instance)->MACCR &= ~ETH_MACCR_TE;
1885
1886 /* Wait until the write operation will be taken into account:
1887 at least four TX_CLK/RX_CLK clock cycles */
1888 tmpreg = (heth->Instance)->MACCR;
1889 HAL_Delay(ETH_REG_WRITE_DELAY);
1890 (heth->Instance)->MACCR = tmpreg;
1891 }
1892
1893 /**
1894 * @brief Enables the MAC reception.
1895 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1896 * the configuration information for ETHERNET module
1897 * @retval None
1898 */
1899 static void ETH_MACReceptionEnable(ETH_HandleTypeDef *heth)
1900 {
1901 __IO uint32_t tmpreg = 0;
1902
1903 /* Enable the MAC reception */
1904 (heth->Instance)->MACCR |= ETH_MACCR_RE;
1905
1906 /* Wait until the write operation will be taken into account:
1907 at least four TX_CLK/RX_CLK clock cycles */
1908 tmpreg = (heth->Instance)->MACCR;
1909 HAL_Delay(ETH_REG_WRITE_DELAY);
1910 (heth->Instance)->MACCR = tmpreg;
1911 }
1912
1913 /**
1914 * @brief Disables the MAC reception.
1915 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1916 * the configuration information for ETHERNET module
1917 * @retval None
1918 */
1919 static void ETH_MACReceptionDisable(ETH_HandleTypeDef *heth)
1920 {
1921 __IO uint32_t tmpreg = 0;
1922
1923 /* Disable the MAC reception */
1924 (heth->Instance)->MACCR &= ~ETH_MACCR_RE;
1925
1926 /* Wait until the write operation will be taken into account:
1927 at least four TX_CLK/RX_CLK clock cycles */
1928 tmpreg = (heth->Instance)->MACCR;
1929 HAL_Delay(ETH_REG_WRITE_DELAY);
1930 (heth->Instance)->MACCR = tmpreg;
1931 }
1932
1933 /**
1934 * @brief Enables the DMA transmission.
1935 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1936 * the configuration information for ETHERNET module
1937 * @retval None
1938 */
1939 static void ETH_DMATransmissionEnable(ETH_HandleTypeDef *heth)
1940 {
1941 /* Enable the DMA transmission */
1942 (heth->Instance)->DMAOMR |= ETH_DMAOMR_ST;
1943 }
1944
1945 /**
1946 * @brief Disables the DMA transmission.
1947 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1948 * the configuration information for ETHERNET module
1949 * @retval None
1950 */
1951 static void ETH_DMATransmissionDisable(ETH_HandleTypeDef *heth)
1952 {
1953 /* Disable the DMA transmission */
1954 (heth->Instance)->DMAOMR &= ~ETH_DMAOMR_ST;
1955 }
1956
1957 /**
1958 * @brief Enables the DMA reception.
1959 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1960 * the configuration information for ETHERNET module
1961 * @retval None
1962 */
1963 static void ETH_DMAReceptionEnable(ETH_HandleTypeDef *heth)
1964 {
1965 /* Enable the DMA reception */
1966 (heth->Instance)->DMAOMR |= ETH_DMAOMR_SR;
1967 }
1968
1969 /**
1970 * @brief Disables the DMA reception.
1971 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1972 * the configuration information for ETHERNET module
1973 * @retval None
1974 */
1975 static void ETH_DMAReceptionDisable(ETH_HandleTypeDef *heth)
1976 {
1977 /* Disable the DMA reception */
1978 (heth->Instance)->DMAOMR &= ~ETH_DMAOMR_SR;
1979 }
1980
1981 /**
1982 * @brief Clears the ETHERNET transmit FIFO.
1983 * @param heth: pointer to a ETH_HandleTypeDef structure that contains
1984 * the configuration information for ETHERNET module
1985 * @retval None
1986 */
1987 static void ETH_FlushTransmitFIFO(ETH_HandleTypeDef *heth)
1988 {
1989 __IO uint32_t tmpreg = 0;
1990
1991 /* Set the Flush Transmit FIFO bit */
1992 (heth->Instance)->DMAOMR |= ETH_DMAOMR_FTF;
1993
1994 /* Wait until the write operation will be taken into account:
1995 at least four TX_CLK/RX_CLK clock cycles */
1996 tmpreg = (heth->Instance)->DMAOMR;
1997 HAL_Delay(ETH_REG_WRITE_DELAY);
1998 (heth->Instance)->DMAOMR = tmpreg;
1999 }
2000
2001 /**
2002 * @}
2003 */
2004
2005 #endif /* STM32F405xx || STM32F415xx || STM32F407xx || STM32F417xx || STM32F427xx || STM32F437xx || STM32F429xx || STM32F439xx */
2006 #endif /* HAL_ETH_MODULE_ENABLED */
2007 /**
2008 * @}
2009 */
2010
2011 /**
2012 * @}
2013 */
2014
2015 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/