diff --git a/drivers/net/usb/r8152.c b/drivers/net/usb/r8152.c
index b6f252722a5eb..6adc198bc92ab 100644
--- a/drivers/net/usb/r8152.c
+++ b/drivers/net/usb/r8152.c
@@ -3714,6 +3714,13 @@ static void r8153_set_rx_early_size(struct r8152 *tp)
}
}
+static void rtl_fc_patch_restart(struct r8152 *tp)
+{
+ ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_FW_TASK, FC_PATCH_TASK);
+ usleep_range(1000, 2000);
+ ocp_word_set_bits(tp, MCU_TYPE_USB, USB_FW_TASK, FC_PATCH_TASK);
+}
+
static int rtl8153_enable(struct r8152 *tp)
{
if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))@@ -3729,9 +3736,7 @@ static int rtl8153_enable(struct r8152 *tp)
switch (tp->version) {
case RTL_VER_09:
case RTL_VER_14:
- ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_FW_TASK, FC_PATCH_TASK);
- usleep_range(1000, 2000);
- ocp_word_set_bits(tp, MCU_TYPE_USB, USB_FW_TASK, FC_PATCH_TASK);
+ rtl_fc_patch_restart(tp);
break;
default:
break;@@ -6509,6 +6514,28 @@ static void r8156_fc_parameter(struct r8152 *tp)
ocp_write_word(tp, MCU_TYPE_PLA, PLA_RX_FIFO_EMPTY, pause_off / 16);
}
+static void r8156_idle_spdwn_en(struct r8152 *tp, u16 speed)
+{
+ if (speed & _2500bps)
+ ocp_word_clr_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL4,
+ IDLE_SPDWN_EN);
+ else
+ ocp_word_set_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL4,
+ IDLE_SPDWN_EN);
+}
+
+static void r8156_l1_nyet_hird(struct r8152 *tp, u16 speed)
+{
+ if (tp->udev->speed != USB_SPEED_HIGH)
+ return;
+
+ /* USB 0xb45e[3:0] l1_nyet_hird */
+ if (is_flow_control(speed))
+ ocp_word_w0w1(tp, MCU_TYPE_USB, USB_L1_CTRL, 0xf, 0xf);
+ else
+ ocp_word_w0w1(tp, MCU_TYPE_USB, USB_L1_CTRL, 0xf, 0x1);
+}
+
static int rtl8156_enable(struct r8152 *tp)
{
u16 speed;@@ -6516,53 +6543,50 @@ static int rtl8156_enable(struct r8152 *tp)
if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
return -ENODEV;
- if (tp->version < RTL_VER_12)
- r8156_fc_parameter(tp);
+ r8156_fc_parameter(tp);
set_tx_qlen(tp);
rtl_set_eee_plus(tp);
-
- if (tp->version >= RTL_VER_12 && tp->version <= RTL_VER_17_QFN100)
- ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_RX_AGGR_NUM, RX_AGGR_NUM_MASK);
-
r8153_set_rx_early_timeout(tp);
r8153_set_rx_early_size(tp);
speed = rtl8152_get_speed(tp);
+ rtl_set_ifg(tp, speed);
- if (tp->version >= RTL_VER_16)
- rtl_fc_pause_pkt_en(tp, speed);
+ r8156_idle_spdwn_en(tp, speed);
- rtl_set_ifg(tp, speed);
+ if (speed & _1000bps)
+ ocp_write_word(tp, MCU_TYPE_PLA, PLA_EEE_TXTWSYS, 0x11);
+ else if (speed & _500bps)
+ ocp_write_word(tp, MCU_TYPE_PLA, PLA_EEE_TXTWSYS, 0x3d);
- if (tp->version >= RTL_VER_16)
- return rtl_enable(tp);
+ r8156_l1_nyet_hird(tp, speed);
+ rtl_fc_patch_restart(tp);
- if (speed & _2500bps)
- ocp_word_clr_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL4,
- IDLE_SPDWN_EN);
- else
- ocp_word_set_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL4,
- IDLE_SPDWN_EN);
+ return rtl_enable(tp);
+}
- if (tp->version < RTL_VER_12) {
- if (speed & _1000bps)
- ocp_write_word(tp, MCU_TYPE_PLA, PLA_EEE_TXTWSYS, 0x11);
- else if (speed & _500bps)
- ocp_write_word(tp, MCU_TYPE_PLA, PLA_EEE_TXTWSYS, 0x3d);
- }
+static int rtl8156b_enable(struct r8152 *tp)
+{
+ u16 speed;
- if (tp->udev->speed == USB_SPEED_HIGH) {
- /* USB 0xb45e[3:0] l1_nyet_hird */
- if (is_flow_control(speed))
- ocp_word_w0w1(tp, MCU_TYPE_USB, USB_L1_CTRL, 0xf, 0xf);
- else
- ocp_word_w0w1(tp, MCU_TYPE_USB, USB_L1_CTRL, 0xf, 0x1);
- }
+ if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
+ return -ENODEV;
- ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_FW_TASK, FC_PATCH_TASK);
- usleep_range(1000, 2000);
- ocp_word_set_bits(tp, MCU_TYPE_USB, USB_FW_TASK, FC_PATCH_TASK);
+ set_tx_qlen(tp);
+ rtl_set_eee_plus(tp);
+
+ ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_RX_AGGR_NUM, RX_AGGR_NUM_MASK);
+
+ r8153_set_rx_early_timeout(tp);
+ r8153_set_rx_early_size(tp);
+
+ speed = rtl8152_get_speed(tp);
+ rtl_set_ifg(tp, speed);
+
+ r8156_idle_spdwn_en(tp, speed);
+ r8156_l1_nyet_hird(tp, speed);
+ rtl_fc_patch_restart(tp);
return rtl_enable(tp);
}@@ -6575,6 +6599,29 @@ static void rtl8156_disable(struct r8152 *tp)
rtl8153_disable(tp);
}
+static int rtl8157_enable(struct r8152 *tp)
+{
+ u16 speed;
+
+ if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
+ return -ENODEV;
+
+ set_tx_qlen(tp);
+ rtl_set_eee_plus(tp);
+
+ ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_RX_AGGR_NUM, RX_AGGR_NUM_MASK);
+
+ r8153_set_rx_early_timeout(tp);
+ r8153_set_rx_early_size(tp);
+
+ speed = rtl8152_get_speed(tp);
+ rtl_fc_pause_pkt_en(tp, speed);
+
+ rtl_set_ifg(tp, speed);
+
+ return rtl_enable(tp);
+}
+
static int rtl8152_set_speed(struct r8152 *tp, u8 autoneg, u32 speed, u8 duplex,
u32 advertising)
{@@ -6929,38 +6976,8 @@ static void rtl8156_change_mtu(struct r8152 *tp)
ALIGN(rx_max_size + tp->tx_desc.size, 1024) / 16);
}
-static void rtl8157_change_mtu(struct r8152 *tp)
+static void r8156_exit_oob(struct r8152 *tp)
{
- u32 max_pkt_size = mtu_to_size(tp->netdev->mtu);
- u32 ocp_data;
-
- ocp_write_word(tp, MCU_TYPE_PLA, PLA_RMS, max_pkt_size);
-
- /* Use at least 10K for MTPS */
- ocp_data = max_t(u32, max_pkt_size, 10 * 1024) / 64;
-
- /* 16 * 1024 / 64 = 0x100, so the max is 0xff for 8 bits data */
- ocp_data = min_t(u32, ocp_data, 0xff);
-
- ocp_write_byte(tp, MCU_TYPE_PLA, PLA_MTPS, ocp_data);
- r8156_fc_parameter(tp);
-
- /* TX share fifo free credit full threshold */
- ocp_write_word(tp, MCU_TYPE_PLA, PLA_TXFIFO_CTRL, 512 / 64);
- ocp_write_word(tp, MCU_TYPE_PLA, PLA_TXFIFO_FULL,
- ALIGN(max_pkt_size + tp->tx_desc.size, 1024) / 16);
-}
-
-static void rtl8156_up(struct r8152 *tp)
-{
- if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
- return;
-
- r8153b_u1u2en(tp, false);
- if (tp->version < RTL_VER_16)
- r8153_u2p3en(tp, false);
- r8153_aldps_en(tp, false);
-
rxdy_gated_en(tp, true);
r8153_teredo_off(tp);
@@ -6992,10 +7009,20 @@ static void rtl8156_up(struct r8152 *tp)
/* share FIFO settings */
ocp_word_w0w1(tp, MCU_TYPE_PLA, PLA_RXFIFO_FULL, RXFIFO_FULL_MASK,
0x08);
+}
- if (tp->version < RTL_VER_16)
- ocp_word_clr_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL3,
- PLA_MCU_SPDWN_EN);
+static void rtl8156_up(struct r8152 *tp)
+{
+ if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
+ return;
+
+ r8153b_u1u2en(tp, false);
+ r8153_u2p3en(tp, false);
+ r8153_aldps_en(tp, false);
+
+ r8156_exit_oob(tp);
+
+ ocp_word_clr_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL3, PLA_MCU_SPDWN_EN);
ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_SPEED_OPTION,
RG_PWRDN_EN | ALL_SPEED_OFF);@@ -7008,8 +7035,7 @@ static void rtl8156_up(struct r8152 *tp)
}
r8153_aldps_en(tp, true);
- if (tp->version < RTL_VER_16)
- r8153_u2p3en(tp, true);
+ r8153_u2p3en(tp, true);
switch (tp->version) {
case RTL_VER_13:@@ -7017,40 +7043,16 @@ static void rtl8156_up(struct r8152 *tp)
/* Enable Clear_SDR */
ocp_word_set_bits(tp, MCU_TYPE_USB, 0xd3ca, BIT(15));
break;
- case RTL_VER_16:
- case RTL_VER_17_QFN68:
- case RTL_VER_17_QFN100:
- /* Enable Clear_SDR */
- ocp_byte_set_bits(tp, MCU_TYPE_USB, 0xd378, BIT(7));
- /* Clear SDR bit */
- ocp_word_clr_bits(tp, MCU_TYPE_USB, 0xcd06, BIT(15));
- break;
default:
break;
}
- if (tp->version < RTL_VER_16 && tp->udev->speed >= USB_SPEED_SUPER)
+ if (tp->udev->speed >= USB_SPEED_SUPER)
r8153b_u1u2en(tp, true);
}
-static void rtl8156_down(struct r8152 *tp)
+static void r8156_enter_oob(struct r8152 *tp)
{
- if (test_bit(RTL8152_INACCESSIBLE, &tp->flags)) {
- rtl_drop_queued_tx(tp);
- return;
- }
-
- if (tp->version < RTL_VER_16)
- ocp_word_set_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL3,
- PLA_MCU_SPDWN_EN);
-
- r8153b_u1u2en(tp, false);
- if (tp->version < RTL_VER_16) {
- r8153_u2p3en(tp, false);
- r8153b_power_cut_en(tp, false);
- }
- r8153_aldps_en(tp, false);
-
ocp_byte_clr_bits(tp, MCU_TYPE_PLA, PLA_OOB_CTRL, NOW_IS_OOB);
/* RX FIFO settings for OOB */@@ -7092,7 +7094,85 @@ static void rtl8156_down(struct r8152 *tp)
ocp_dword_set_bits(tp, MCU_TYPE_PLA, PLA_RCR,
RCR_APM | RCR_AM | RCR_AB);
+}
+
+static void rtl8156_down(struct r8152 *tp)
+{
+ if (test_bit(RTL8152_INACCESSIBLE, &tp->flags)) {
+ rtl_drop_queued_tx(tp);
+ return;
+ }
+ ocp_word_set_bits(tp, MCU_TYPE_PLA, PLA_MAC_PWR_CTRL3,
+ PLA_MCU_SPDWN_EN);
+
+ r8153b_u1u2en(tp, false);
+ r8153_u2p3en(tp, false);
+ r8153b_power_cut_en(tp, false);
+ r8153_aldps_en(tp, false);
+ r8156_enter_oob(tp);
+ r8153_aldps_en(tp, true);
+}
+
+static void rtl8157_change_mtu(struct r8152 *tp)
+{
+ u32 max_pkt_size = mtu_to_size(tp->netdev->mtu);
+ u32 ocp_data;
+
+ ocp_write_word(tp, MCU_TYPE_PLA, PLA_RMS, max_pkt_size);
+
+ /* Use at least 10K for MTPS */
+ ocp_data = max_t(u32, max_pkt_size, 10 * 1024) / 64;
+
+ /* 16 * 1024 / 64 = 0x100, so the max is 0xff for 8 bits data */
+ ocp_data = min_t(u32, ocp_data, 0xff);
+
+ ocp_write_byte(tp, MCU_TYPE_PLA, PLA_MTPS, ocp_data);
+ r8156_fc_parameter(tp);
+
+ /* TX share fifo free credit full threshold */
+ ocp_write_word(tp, MCU_TYPE_PLA, PLA_TXFIFO_CTRL, 512 / 64);
+ ocp_write_word(tp, MCU_TYPE_PLA, PLA_TXFIFO_FULL,
+ ALIGN(max_pkt_size + tp->tx_desc.size, 1024) / 16);
+}
+
+static void rtl8157_up(struct r8152 *tp)
+{
+ if (test_bit(RTL8152_INACCESSIBLE, &tp->flags))
+ return;
+
+ r8153b_u1u2en(tp, false);
+ r8153_aldps_en(tp, false);
+ r8156_exit_oob(tp);
+
+ ocp_word_clr_bits(tp, MCU_TYPE_USB, USB_SPEED_OPTION,
+ RG_PWRDN_EN | ALL_SPEED_OFF);
+
+ ocp_write_dword(tp, MCU_TYPE_USB, USB_RX_BUF_TH, 0x00600400);
+
+ if (tp->saved_wolopts != __rtl_get_wol(tp)) {
+ netif_warn(tp, ifup, tp->netdev, "wol setting is changed\n");
+ __rtl_set_wol(tp, tp->saved_wolopts);
+ }
+
+ r8153_aldps_en(tp, true);
+
+ /* Enable Clear_SDR */
+ ocp_byte_set_bits(tp, MCU_TYPE_USB, 0xd378, BIT(7));
+ /* Clear SDR bit */
+ ocp_word_clr_bits(tp, MCU_TYPE_USB, 0xcd06, BIT(15));
+}
+
+static void rtl8157_down(struct r8152 *tp)
+{
+ if (test_bit(RTL8152_INACCESSIBLE, &tp->flags)) {
+ rtl_drop_queued_tx(tp);
+ return;
+ }
+
+ r8153b_u1u2en(tp, false);
+ r8153_aldps_en(tp, false);
+ r8156_enter_oob(tp);
r8153_aldps_en(tp, true);
}
@@ -10094,7 +10174,7 @@ static int rtl_ops_init(struct r8152 *tp)
tp->eee_adv = MDIO_EEE_1000T | MDIO_EEE_100TX;
tp->eee_adv2 = MDIO_EEE_2_5GT;
ops->init = r8156_init;
- ops->enable = rtl8156_enable;
+ ops->enable = rtl8156b_enable;
ops->disable = rtl8153_disable;
ops->up = rtl8156_up;
ops->down = rtl8156_down;
@@ -10133,10 +10213,10 @@ static int rtl_ops_init(struct r8152 *tp)
tp->eee_adv = MDIO_EEE_1000T | MDIO_EEE_100TX;
tp->eee_adv2 = MDIO_EEE_2_5GT | MDIO_EEE_5GT;
ops->init = r8157_init;
- ops->enable = rtl8156_enable;
+ ops->enable = rtl8157_enable;
ops->disable = rtl8153_disable;
- ops->up = rtl8156_up;
- ops->down = rtl8156_down;
+ ops->up = rtl8157_up;
+ ops->down = rtl8157_down;
ops->unload = rtl8157_unload;
ops->eee_get = r8153_get_eee;
ops->eee_set = r8152_set_eee;
@@ -10156,10 +10236,10 @@ static int rtl_ops_init(struct r8152 *tp)
tp->eee_adv = MDIO_EEE_100TX | MDIO_EEE_1000T | MDIO_EEE_10GT;
tp->eee_adv2 = MDIO_EEE_2_5GT | MDIO_EEE_5GT;
ops->init = r8157_init;
- ops->enable = rtl8156_enable;
+ ops->enable = rtl8157_enable;
ops->disable = rtl8153_disable;
- ops->up = rtl8156_up;
- ops->down = rtl8156_down;
+ ops->up = rtl8157_up;
+ ops->down = rtl8157_down;
ops->unload = rtl8157_unload;
ops->eee_get = r8153_get_eee;
ops->eee_set = r8152_set_eee;
--
2.34.1