@@ -1684,6 +1684,8 @@ int qed_hw_init(struct qed_dev *cdev, struct qed_hw_init_params *p_params)
1684
1684
"Load request was sent. Load code: 0x%x\n" ,
1685
1685
load_code );
1686
1686
1687
+ qed_mcp_set_capabilities (p_hwfn , p_hwfn -> p_main_ptt );
1688
+
1687
1689
qed_reset_mb_shadow (p_hwfn , p_hwfn -> p_main_ptt );
1688
1690
1689
1691
p_hwfn -> first_on_engine = (load_code ==
@@ -2472,6 +2474,7 @@ static int qed_hw_get_nvm_info(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt)
2472
2474
{
2473
2475
u32 port_cfg_addr , link_temp , nvm_cfg_addr , device_capabilities ;
2474
2476
u32 nvm_cfg1_offset , mf_mode , addr , generic_cont0 , core_cfg ;
2477
+ struct qed_mcp_link_capabilities * p_caps ;
2475
2478
struct qed_mcp_link_params * link ;
2476
2479
2477
2480
/* Read global nvm_cfg address */
@@ -2534,6 +2537,7 @@ static int qed_hw_get_nvm_info(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt)
2534
2537
2535
2538
/* Read default link configuration */
2536
2539
link = & p_hwfn -> mcp_info -> link_input ;
2540
+ p_caps = & p_hwfn -> mcp_info -> link_capabilities ;
2537
2541
port_cfg_addr = MCP_REG_SCRATCH + nvm_cfg1_offset +
2538
2542
offsetof(struct nvm_cfg1 , port [MFW_PORT (p_hwfn )]);
2539
2543
link_temp = qed_rd (p_hwfn , p_ptt ,
@@ -2588,10 +2592,45 @@ static int qed_hw_get_nvm_info(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt)
2588
2592
NVM_CFG1_PORT_DRV_FLOW_CONTROL_TX );
2589
2593
link -> loopback_mode = 0 ;
2590
2594
2591
- DP_VERBOSE (p_hwfn , NETIF_MSG_LINK ,
2592
- "Read default link: Speed 0x%08x, Adv. Speed 0x%08x, AN: 0x%02x, PAUSE AN: 0x%02x\n" ,
2593
- link -> speed .forced_speed , link -> speed .advertised_speeds ,
2594
- link -> speed .autoneg , link -> pause .autoneg );
2595
+ if (p_hwfn -> mcp_info -> capabilities & FW_MB_PARAM_FEATURE_SUPPORT_EEE ) {
2596
+ link_temp = qed_rd (p_hwfn , p_ptt , port_cfg_addr +
2597
+ offsetof(struct nvm_cfg1_port , ext_phy ));
2598
+ link_temp &= NVM_CFG1_PORT_EEE_POWER_SAVING_MODE_MASK ;
2599
+ link_temp >>= NVM_CFG1_PORT_EEE_POWER_SAVING_MODE_OFFSET ;
2600
+ p_caps -> default_eee = QED_MCP_EEE_ENABLED ;
2601
+ link -> eee .enable = true;
2602
+ switch (link_temp ) {
2603
+ case NVM_CFG1_PORT_EEE_POWER_SAVING_MODE_DISABLED :
2604
+ p_caps -> default_eee = QED_MCP_EEE_DISABLED ;
2605
+ link -> eee .enable = false;
2606
+ break ;
2607
+ case NVM_CFG1_PORT_EEE_POWER_SAVING_MODE_BALANCED :
2608
+ p_caps -> eee_lpi_timer = EEE_TX_TIMER_USEC_BALANCED_TIME ;
2609
+ break ;
2610
+ case NVM_CFG1_PORT_EEE_POWER_SAVING_MODE_AGGRESSIVE :
2611
+ p_caps -> eee_lpi_timer =
2612
+ EEE_TX_TIMER_USEC_AGGRESSIVE_TIME ;
2613
+ break ;
2614
+ case NVM_CFG1_PORT_EEE_POWER_SAVING_MODE_LOW_LATENCY :
2615
+ p_caps -> eee_lpi_timer = EEE_TX_TIMER_USEC_LATENCY_TIME ;
2616
+ break ;
2617
+ }
2618
+
2619
+ link -> eee .tx_lpi_timer = p_caps -> eee_lpi_timer ;
2620
+ link -> eee .tx_lpi_enable = link -> eee .enable ;
2621
+ link -> eee .adv_caps = QED_EEE_1G_ADV | QED_EEE_10G_ADV ;
2622
+ } else {
2623
+ p_caps -> default_eee = QED_MCP_EEE_UNSUPPORTED ;
2624
+ }
2625
+
2626
+ DP_VERBOSE (p_hwfn ,
2627
+ NETIF_MSG_LINK ,
2628
+ "Read default link: Speed 0x%08x, Adv. Speed 0x%08x, AN: 0x%02x, PAUSE AN: 0x%02x EEE: %02x [%08x usec]\n" ,
2629
+ link -> speed .forced_speed ,
2630
+ link -> speed .advertised_speeds ,
2631
+ link -> speed .autoneg ,
2632
+ link -> pause .autoneg ,
2633
+ p_caps -> default_eee , p_caps -> eee_lpi_timer );
2595
2634
2596
2635
/* Read Multi-function information from shmem */
2597
2636
addr = MCP_REG_SCRATCH + nvm_cfg1_offset +
@@ -2751,6 +2790,27 @@ static void qed_hw_info_port_num(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt)
2751
2790
qed_hw_info_port_num_ah (p_hwfn , p_ptt );
2752
2791
}
2753
2792
2793
+ static void qed_get_eee_caps (struct qed_hwfn * p_hwfn , struct qed_ptt * p_ptt )
2794
+ {
2795
+ struct qed_mcp_link_capabilities * p_caps ;
2796
+ u32 eee_status ;
2797
+
2798
+ p_caps = & p_hwfn -> mcp_info -> link_capabilities ;
2799
+ if (p_caps -> default_eee == QED_MCP_EEE_UNSUPPORTED )
2800
+ return ;
2801
+
2802
+ p_caps -> eee_speed_caps = 0 ;
2803
+ eee_status = qed_rd (p_hwfn , p_ptt , p_hwfn -> mcp_info -> port_addr +
2804
+ offsetof(struct public_port , eee_status ));
2805
+ eee_status = (eee_status & EEE_SUPPORTED_SPEED_MASK ) >>
2806
+ EEE_SUPPORTED_SPEED_OFFSET ;
2807
+
2808
+ if (eee_status & EEE_1G_SUPPORTED )
2809
+ p_caps -> eee_speed_caps |= QED_EEE_1G_ADV ;
2810
+ if (eee_status & EEE_10G_ADV )
2811
+ p_caps -> eee_speed_caps |= QED_EEE_10G_ADV ;
2812
+ }
2813
+
2754
2814
static int
2755
2815
qed_get_hw_info (struct qed_hwfn * p_hwfn ,
2756
2816
struct qed_ptt * p_ptt ,
@@ -2767,6 +2827,8 @@ qed_get_hw_info(struct qed_hwfn *p_hwfn,
2767
2827
2768
2828
qed_hw_info_port_num (p_hwfn , p_ptt );
2769
2829
2830
+ qed_mcp_get_capabilities (p_hwfn , p_ptt );
2831
+
2770
2832
qed_hw_get_nvm_info (p_hwfn , p_ptt );
2771
2833
2772
2834
rc = qed_int_igu_read_cam (p_hwfn , p_ptt );
@@ -2785,6 +2847,8 @@ qed_get_hw_info(struct qed_hwfn *p_hwfn,
2785
2847
p_hwfn -> mcp_info -> func_info .ovlan ;
2786
2848
2787
2849
qed_mcp_cmd_port_init (p_hwfn , p_ptt );
2850
+
2851
+ qed_get_eee_caps (p_hwfn , p_ptt );
2788
2852
}
2789
2853
2790
2854
if (qed_mcp_is_init (p_hwfn )) {
@@ -3630,20 +3694,54 @@ static int qed_set_coalesce(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt,
3630
3694
}
3631
3695
3632
3696
p_coal_timeset = p_eth_qzone ;
3633
- memset (p_coal_timeset , 0 , eth_qzone_size );
3697
+ memset (p_eth_qzone , 0 , eth_qzone_size );
3634
3698
SET_FIELD (p_coal_timeset -> value , COALESCING_TIMESET_TIMESET , timeset );
3635
3699
SET_FIELD (p_coal_timeset -> value , COALESCING_TIMESET_VALID , 1 );
3636
3700
qed_memcpy_to (p_hwfn , p_ptt , hw_addr , p_eth_qzone , eth_qzone_size );
3637
3701
3638
3702
return 0 ;
3639
3703
}
3640
3704
3641
- int qed_set_rxq_coalesce (struct qed_hwfn * p_hwfn , struct qed_ptt * p_ptt ,
3642
- u16 coalesce , u16 qid , u16 sb_id )
3705
+ int qed_set_queue_coalesce (u16 rx_coal , u16 tx_coal , void * p_handle )
3706
+ {
3707
+ struct qed_queue_cid * p_cid = p_handle ;
3708
+ struct qed_hwfn * p_hwfn ;
3709
+ struct qed_ptt * p_ptt ;
3710
+ int rc = 0 ;
3711
+
3712
+ p_hwfn = p_cid -> p_owner ;
3713
+
3714
+ if (IS_VF (p_hwfn -> cdev ))
3715
+ return qed_vf_pf_set_coalesce (p_hwfn , rx_coal , tx_coal , p_cid );
3716
+
3717
+ p_ptt = qed_ptt_acquire (p_hwfn );
3718
+ if (!p_ptt )
3719
+ return - EAGAIN ;
3720
+
3721
+ if (rx_coal ) {
3722
+ rc = qed_set_rxq_coalesce (p_hwfn , p_ptt , rx_coal , p_cid );
3723
+ if (rc )
3724
+ goto out ;
3725
+ p_hwfn -> cdev -> rx_coalesce_usecs = rx_coal ;
3726
+ }
3727
+
3728
+ if (tx_coal ) {
3729
+ rc = qed_set_txq_coalesce (p_hwfn , p_ptt , tx_coal , p_cid );
3730
+ if (rc )
3731
+ goto out ;
3732
+ p_hwfn -> cdev -> tx_coalesce_usecs = tx_coal ;
3733
+ }
3734
+ out :
3735
+ qed_ptt_release (p_hwfn , p_ptt );
3736
+ return rc ;
3737
+ }
3738
+
3739
+ int qed_set_rxq_coalesce (struct qed_hwfn * p_hwfn ,
3740
+ struct qed_ptt * p_ptt ,
3741
+ u16 coalesce , struct qed_queue_cid * p_cid )
3643
3742
{
3644
3743
struct ustorm_eth_queue_zone eth_qzone ;
3645
3744
u8 timeset , timer_res ;
3646
- u16 fw_qid = 0 ;
3647
3745
u32 address ;
3648
3746
int rc ;
3649
3747
@@ -3660,32 +3758,29 @@ int qed_set_rxq_coalesce(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt,
3660
3758
}
3661
3759
timeset = (u8 )(coalesce >> timer_res );
3662
3760
3663
- rc = qed_fw_l2_queue (p_hwfn , qid , & fw_qid );
3664
- if (rc )
3665
- return rc ;
3666
-
3667
- rc = qed_int_set_timer_res (p_hwfn , p_ptt , timer_res , sb_id , false);
3761
+ rc = qed_int_set_timer_res (p_hwfn , p_ptt , timer_res ,
3762
+ p_cid -> sb_igu_id , false);
3668
3763
if (rc )
3669
3764
goto out ;
3670
3765
3671
- address = BAR0_MAP_REG_USDM_RAM + USTORM_ETH_QUEUE_ZONE_OFFSET (fw_qid );
3766
+ address = BAR0_MAP_REG_USDM_RAM +
3767
+ USTORM_ETH_QUEUE_ZONE_OFFSET (p_cid -> abs .queue_id );
3672
3768
3673
3769
rc = qed_set_coalesce (p_hwfn , p_ptt , address , & eth_qzone ,
3674
3770
sizeof (struct ustorm_eth_queue_zone ), timeset );
3675
3771
if (rc )
3676
3772
goto out ;
3677
3773
3678
- p_hwfn -> cdev -> rx_coalesce_usecs = coalesce ;
3679
3774
out :
3680
3775
return rc ;
3681
3776
}
3682
3777
3683
- int qed_set_txq_coalesce (struct qed_hwfn * p_hwfn , struct qed_ptt * p_ptt ,
3684
- u16 coalesce , u16 qid , u16 sb_id )
3778
+ int qed_set_txq_coalesce (struct qed_hwfn * p_hwfn ,
3779
+ struct qed_ptt * p_ptt ,
3780
+ u16 coalesce , struct qed_queue_cid * p_cid )
3685
3781
{
3686
3782
struct xstorm_eth_queue_zone eth_qzone ;
3687
3783
u8 timeset , timer_res ;
3688
- u16 fw_qid = 0 ;
3689
3784
u32 address ;
3690
3785
int rc ;
3691
3786
@@ -3702,22 +3797,16 @@ int qed_set_txq_coalesce(struct qed_hwfn *p_hwfn, struct qed_ptt *p_ptt,
3702
3797
}
3703
3798
timeset = (u8 )(coalesce >> timer_res );
3704
3799
3705
- rc = qed_fw_l2_queue (p_hwfn , qid , & fw_qid );
3706
- if (rc )
3707
- return rc ;
3708
-
3709
- rc = qed_int_set_timer_res (p_hwfn , p_ptt , timer_res , sb_id , true);
3800
+ rc = qed_int_set_timer_res (p_hwfn , p_ptt , timer_res ,
3801
+ p_cid -> sb_igu_id , true);
3710
3802
if (rc )
3711
3803
goto out ;
3712
3804
3713
- address = BAR0_MAP_REG_XSDM_RAM + XSTORM_ETH_QUEUE_ZONE_OFFSET (fw_qid );
3805
+ address = BAR0_MAP_REG_XSDM_RAM +
3806
+ XSTORM_ETH_QUEUE_ZONE_OFFSET (p_cid -> abs .queue_id );
3714
3807
3715
3808
rc = qed_set_coalesce (p_hwfn , p_ptt , address , & eth_qzone ,
3716
3809
sizeof (struct xstorm_eth_queue_zone ), timeset );
3717
- if (rc )
3718
- goto out ;
3719
-
3720
- p_hwfn -> cdev -> tx_coalesce_usecs = coalesce ;
3721
3810
out :
3722
3811
return rc ;
3723
3812
}
0 commit comments