|
7 | 7 | * Date Author Notes |
8 | 8 | * 2018-11-19 SummerGift first version |
9 | 9 | * 2018-12-25 zylx fix some bugs |
10 | | - * 2019-06-10 SummerGift optimize PHY state detection process |
| 10 | + * 2019-06-10 SummerGift optimize PHY state detection process |
| 11 | + * 2019-09-03 xiaofan optimize link change detection process |
11 | 12 | */ |
12 | 13 |
|
13 | 14 | #include "board.h" |
@@ -390,47 +391,94 @@ void HAL_ETH_ErrorCallback(ETH_HandleTypeDef *heth) |
390 | 391 | LOG_E("eth err"); |
391 | 392 | } |
392 | 393 |
|
393 | | -#ifdef PHY_USING_INTERRUPT_MODE |
394 | | -static void eth_phy_isr(void *args) |
| 394 | +enum { |
| 395 | + PHY_LINK = (1 << 0), |
| 396 | + PHY_100M = (1 << 1), |
| 397 | + PHY_FULL_DUPLEX = (1 << 2), |
| 398 | +}; |
| 399 | + |
| 400 | +static void phy_linkchange() |
395 | 401 | { |
396 | | - rt_uint32_t status = 0; |
397 | | - static rt_uint8_t link_status = 1; |
| 402 | + static rt_uint8_t phy_speed = 0; |
| 403 | + rt_uint8_t phy_speed_new = 0; |
| 404 | + rt_uint32_t status; |
398 | 405 |
|
399 | | - HAL_ETH_ReadPHYRegister(&EthHandle, PHY_INTERRUPT_FLAG_REG, (uint32_t *)&status); |
400 | | - LOG_D("phy interrupt status reg is 0x%X", status); |
401 | 406 | HAL_ETH_ReadPHYRegister(&EthHandle, PHY_BASIC_STATUS_REG, (uint32_t *)&status); |
402 | 407 | LOG_D("phy basic status reg is 0x%X", status); |
403 | 408 |
|
404 | | - if (status & PHY_LINKED_STATUS_MASK) |
| 409 | + if (status & (PHY_AUTONEGO_COMPLETE_MASK | PHY_LINKED_STATUS_MASK)) |
405 | 410 | { |
406 | | - if (link_status == 0) |
| 411 | + rt_uint32_t SR; |
| 412 | + |
| 413 | + phy_speed_new |= PHY_LINK; |
| 414 | + |
| 415 | + SR = HAL_ETH_ReadPHYRegister(&EthHandle, PHY_Status_REG, (uint32_t *)&SR); |
| 416 | + LOG_D("phy control status reg is 0x%X", SR); |
| 417 | + |
| 418 | + if (PHY_Status_SPEED_100M(SR)) |
| 419 | + { |
| 420 | + phy_speed_new |= PHY_100M; |
| 421 | + } |
| 422 | + |
| 423 | + if (PHY_Status_FULL_DUPLEX(SR)) |
| 424 | + { |
| 425 | + phy_speed_new |= PHY_FULL_DUPLEX; |
| 426 | + } |
| 427 | + } |
| 428 | + |
| 429 | + if (phy_speed != phy_speed_new) { |
| 430 | + phy_speed = phy_speed_new; |
| 431 | + if (phy_speed & PHY_LINK) |
407 | 432 | { |
408 | | - link_status = 1; |
409 | 433 | LOG_D("link up"); |
| 434 | + if (phy_speed & PHY_100M) |
| 435 | + { |
| 436 | + LOG_D("100Mbps"); |
| 437 | + stm32_eth_device.ETH_Speed = ETH_SPEED_100M; |
| 438 | + } |
| 439 | + else |
| 440 | + { |
| 441 | + stm32_eth_device.ETH_Speed = ETH_SPEED_10M; |
| 442 | + LOG_D("10Mbps"); |
| 443 | + } |
| 444 | + |
| 445 | + if (phy_speed & PHY_FULL_DUPLEX) |
| 446 | + { |
| 447 | + LOG_D("full-duplex"); |
| 448 | + stm32_eth_device.ETH_Mode = ETH_MODE_FULLDUPLEX; |
| 449 | + } |
| 450 | + else |
| 451 | + { |
| 452 | + LOG_D("half-duplex"); |
| 453 | + stm32_eth_device.ETH_Mode = ETH_MODE_HALFDUPLEX; |
| 454 | + } |
| 455 | + |
410 | 456 | /* send link up. */ |
411 | 457 | eth_device_linkchange(&stm32_eth_device.parent, RT_TRUE); |
412 | 458 | } |
413 | | - } |
414 | | - else |
415 | | - { |
416 | | - if (link_status == 1) |
| 459 | + else |
417 | 460 | { |
418 | | - link_status = 0; |
419 | 461 | LOG_I("link down"); |
420 | | - /* send link down. */ |
421 | 462 | eth_device_linkchange(&stm32_eth_device.parent, RT_FALSE); |
422 | 463 | } |
423 | 464 | } |
424 | 465 | } |
| 466 | + |
| 467 | +#ifdef PHY_USING_INTERRUPT_MODE |
| 468 | +static void eth_phy_isr(void *args) |
| 469 | +{ |
| 470 | + rt_uint32_t status = 0; |
| 471 | + |
| 472 | + HAL_ETH_ReadPHYRegister(&EthHandle, PHY_INTERRUPT_FLAG_REG, (uint32_t *)&status); |
| 473 | + LOG_D("phy interrupt status reg is 0x%X", status); |
| 474 | + |
| 475 | + phy_linkchange(); |
| 476 | +} |
425 | 477 | #endif /* PHY_USING_INTERRUPT_MODE */ |
426 | 478 |
|
427 | | -static uint8_t phy_speed = 0; |
428 | | -#define PHY_LINK_MASK (1<<0) |
429 | 479 | static void phy_monitor_thread_entry(void *parameter) |
430 | 480 | { |
431 | 481 | uint8_t phy_addr = 0xFF; |
432 | | - uint8_t phy_speed_new = 0; |
433 | | - rt_uint32_t status = 0; |
434 | 482 | uint8_t detected_count = 0; |
435 | 483 |
|
436 | 484 | while(phy_addr == 0xFF) |
@@ -468,102 +516,29 @@ static void phy_monitor_thread_entry(void *parameter) |
468 | 516 |
|
469 | 517 | while (1) |
470 | 518 | { |
471 | | - phy_speed_new = 0; |
| 519 | + phy_linkchange(); |
472 | 520 |
|
473 | | - if(HAL_ETH_ReadPHYRegister(&EthHandle, PHY_BASIC_STATUS_REG, (uint32_t *)&status) == HAL_OK) |
474 | | - { |
475 | | - LOG_D("PHY BASIC STATUS REG:0x%04X", status); |
476 | | - |
477 | | - if (status & (PHY_AUTONEGO_COMPLETE_MASK | PHY_LINKED_STATUS_MASK)) |
478 | | - { |
479 | | - rt_uint32_t SR; |
480 | | - |
481 | | - phy_speed_new = PHY_LINK_MASK; |
482 | | - |
483 | | - if(HAL_ETH_ReadPHYRegister(&EthHandle, PHY_Status_REG, (uint32_t *)&SR) == HAL_OK) |
484 | | - { |
485 | | - LOG_D("PHY Control/Status REG:0x%04X ", SR); |
486 | | - |
487 | | - if (SR & PHY_100M_MASK) |
488 | | - { |
489 | | - phy_speed_new |= PHY_100M_MASK; |
490 | | - } |
491 | | - else if (SR & PHY_10M_MASK) |
492 | | - { |
493 | | - phy_speed_new |= PHY_10M_MASK; |
494 | | - } |
495 | | - |
496 | | - if (SR & PHY_FULL_DUPLEX_MASK) |
497 | | - { |
498 | | - phy_speed_new |= PHY_FULL_DUPLEX_MASK; |
499 | | - } |
500 | | - } |
501 | | - else |
502 | | - { |
503 | | - LOG_D("PHY PHY_Status_REG read error."); |
504 | | - rt_thread_mdelay(100); |
505 | | - continue; |
506 | | - } |
507 | | - } |
508 | | - } |
509 | | - else |
| 521 | + if (stm32_eth_device.parent.netif->flags & NETIF_FLAG_LINK_UP) |
510 | 522 | { |
511 | | - LOG_D("PHY_BASIC_STATUS_REG read error."); |
512 | | - rt_thread_mdelay(100); |
513 | | - continue; |
514 | | - } |
515 | | - |
516 | | - /* linkchange */ |
517 | | - if (phy_speed_new != phy_speed) |
518 | | - { |
519 | | - if (phy_speed_new & PHY_LINK_MASK) |
520 | | - { |
521 | | - LOG_D("link up "); |
522 | | - |
523 | | - if (phy_speed_new & PHY_100M_MASK) |
524 | | - { |
525 | | - LOG_D("100Mbps"); |
526 | | - stm32_eth_device.ETH_Speed = ETH_SPEED_100M; |
527 | | - } |
528 | | - else |
529 | | - { |
530 | | - stm32_eth_device.ETH_Speed = ETH_SPEED_10M; |
531 | | - LOG_D("10Mbps"); |
532 | | - } |
533 | | - |
534 | | - if (phy_speed_new & PHY_FULL_DUPLEX_MASK) |
535 | | - { |
536 | | - LOG_D("full-duplex"); |
537 | | - stm32_eth_device.ETH_Mode = ETH_MODE_FULLDUPLEX; |
538 | | - } |
539 | | - else |
540 | | - { |
541 | | - LOG_D("half-duplex"); |
542 | | - stm32_eth_device.ETH_Mode = ETH_MODE_HALFDUPLEX; |
543 | | - } |
544 | | - |
545 | | - /* send link up. */ |
546 | | - eth_device_linkchange(&stm32_eth_device.parent, RT_TRUE); |
547 | | - |
548 | 523 | #ifdef PHY_USING_INTERRUPT_MODE |
549 | | - /* configuration intterrupt pin */ |
550 | | - rt_pin_mode(PHY_INT_PIN, PIN_MODE_INPUT_PULLUP); |
551 | | - rt_pin_attach_irq(PHY_INT_PIN, PIN_IRQ_MODE_FALLING, eth_phy_isr, (void *)"callbackargs"); |
552 | | - rt_pin_irq_enable(PHY_INT_PIN, PIN_IRQ_ENABLE); |
553 | | - |
554 | | - /* enable phy interrupt */ |
555 | | - HAL_ETH_WritePHYRegister(&EthHandle, PHY_INTERRUPT_MSAK_REG, PHY_INT_MASK); |
556 | | - |
557 | | - break; |
| 524 | + /* configuration intterrupt pin */ |
| 525 | + rt_pin_mode(PHY_INT_PIN, PIN_MODE_INPUT_PULLUP); |
| 526 | + rt_pin_attach_irq(PHY_INT_PIN, PIN_IRQ_MODE_FALLING, eth_phy_isr, (void *)"callbackargs"); |
| 527 | + rt_pin_irq_enable(PHY_INT_PIN, PIN_IRQ_ENABLE); |
| 528 | + |
| 529 | + /* enable phy interrupt */ |
| 530 | + HAL_ETH_WritePHYRegister(&EthHandle, PHY_INTERRUPT_MASK_REG, PHY_INT_MASK); |
| 531 | +#if defined(PHY_INTERRUPT_CTRL_REG) |
| 532 | + HAL_ETH_WritePHYRegister(&EthHandle, PHY_INTERRUPT_CTRL_REG, PHY_INTERRUPT_EN); |
558 | 533 | #endif |
559 | | - } /* link up. */ |
560 | | - else |
561 | | - { |
562 | | - LOG_I("link down"); |
563 | | - /* send link down. */ |
564 | | - eth_device_linkchange(&stm32_eth_device.parent, RT_FALSE); |
565 | | - } |
566 | | - phy_speed = phy_speed_new; |
| 534 | + break; |
| 535 | +#endif |
| 536 | + } /* link up. */ |
| 537 | + else |
| 538 | + { |
| 539 | + LOG_I("link down"); |
| 540 | + /* send link down. */ |
| 541 | + eth_device_linkchange(&stm32_eth_device.parent, RT_FALSE); |
567 | 542 | } |
568 | 543 |
|
569 | 544 | rt_thread_delay(RT_TICK_PER_SECOND); |
|
0 commit comments