diff options
| author | Francois Romieu <romieu@fr.zoreil.com> | 2012-07-06 08:19:23 -0400 |
|---|---|---|
| committer | Francois Romieu <romieu@fr.zoreil.com> | 2012-07-09 17:38:22 -0400 |
| commit | ffc46952b313ff037debca1b4e3da9472ff4b441 (patch) | |
| tree | 9ce60ab5785d1c0d3a08181905629065bb5d1d37 | |
| parent | fdf6fc067aaeb13aba89d1b56aa39d3bf06fde43 (diff) | |
r8169: abstract out loop conditions.
Twelve functions can fail silently. Now they have a chance to complain.
Macro and pasting abuse has been kept at a level where tags and
friends should not be hurt.
Signed-off-by: Francois Romieu <romieu@fr.zoreil.com>
| -rw-r--r-- | drivers/net/ethernet/realtek/r8169.c | 367 |
1 files changed, 186 insertions, 181 deletions
diff --git a/drivers/net/ethernet/realtek/r8169.c b/drivers/net/ethernet/realtek/r8169.c index 7c6c4b253ea1..eb6fdeff5adf 100644 --- a/drivers/net/ethernet/realtek/r8169.c +++ b/drivers/net/ethernet/realtek/r8169.c | |||
| @@ -826,47 +826,113 @@ static void rtl_tx_performance_tweak(struct pci_dev *pdev, u16 force) | |||
| 826 | } | 826 | } |
| 827 | } | 827 | } |
| 828 | 828 | ||
| 829 | struct rtl_cond { | ||
| 830 | bool (*check)(struct rtl8169_private *); | ||
| 831 | const char *msg; | ||
| 832 | }; | ||
| 833 | |||
| 834 | static void rtl_udelay(unsigned int d) | ||
| 835 | { | ||
| 836 | udelay(d); | ||
| 837 | } | ||
| 838 | |||
| 839 | static bool rtl_loop_wait(struct rtl8169_private *tp, const struct rtl_cond *c, | ||
| 840 | void (*delay)(unsigned int), unsigned int d, int n, | ||
| 841 | bool high) | ||
| 842 | { | ||
| 843 | int i; | ||
| 844 | |||
| 845 | for (i = 0; i < n; i++) { | ||
| 846 | delay(d); | ||
| 847 | if (c->check(tp) == high) | ||
| 848 | return true; | ||
| 849 | } | ||
| 850 | netif_err(tp, drv, tp->dev, c->msg); | ||
| 851 | return false; | ||
| 852 | } | ||
| 853 | |||
| 854 | static bool rtl_udelay_loop_wait_high(struct rtl8169_private *tp, | ||
| 855 | const struct rtl_cond *c, | ||
| 856 | unsigned int d, int n) | ||
| 857 | { | ||
| 858 | return rtl_loop_wait(tp, c, rtl_udelay, d, n, true); | ||
| 859 | } | ||
| 860 | |||
| 861 | static bool rtl_udelay_loop_wait_low(struct rtl8169_private *tp, | ||
| 862 | const struct rtl_cond *c, | ||
| 863 | unsigned int d, int n) | ||
| 864 | { | ||
| 865 | return rtl_loop_wait(tp, c, rtl_udelay, d, n, false); | ||
| 866 | } | ||
| 867 | |||
| 868 | static bool rtl_msleep_loop_wait_high(struct rtl8169_private *tp, | ||
| 869 | const struct rtl_cond *c, | ||
| 870 | unsigned int d, int n) | ||
| 871 | { | ||
| 872 | return rtl_loop_wait(tp, c, msleep, d, n, true); | ||
| 873 | } | ||
| 874 | |||
| 875 | static bool rtl_msleep_loop_wait_low(struct rtl8169_private *tp, | ||
| 876 | const struct rtl_cond *c, | ||
| 877 | unsigned int d, int n) | ||
| 878 | { | ||
| 879 | return rtl_loop_wait(tp, c, msleep, d, n, false); | ||
| 880 | } | ||
| 881 | |||
| 882 | #define DECLARE_RTL_COND(name) \ | ||
| 883 | static bool name ## _check(struct rtl8169_private *); \ | ||
| 884 | \ | ||
| 885 | static const struct rtl_cond name = { \ | ||
| 886 | .check = name ## _check, \ | ||
| 887 | .msg = #name \ | ||
| 888 | }; \ | ||
| 889 | \ | ||
| 890 | static bool name ## _check(struct rtl8169_private *tp) | ||
| 891 | |||
| 892 | DECLARE_RTL_COND(rtl_ocpar_cond) | ||
| 893 | { | ||
| 894 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 895 | |||
| 896 | return RTL_R32(OCPAR) & OCPAR_FLAG; | ||
| 897 | } | ||
| 898 | |||
| 829 | static u32 ocp_read(struct rtl8169_private *tp, u8 mask, u16 reg) | 899 | static u32 ocp_read(struct rtl8169_private *tp, u8 mask, u16 reg) |
| 830 | { | 900 | { |
| 831 | void __iomem *ioaddr = tp->mmio_addr; | 901 | void __iomem *ioaddr = tp->mmio_addr; |
| 832 | int i; | ||
| 833 | 902 | ||
| 834 | RTL_W32(OCPAR, ((u32)mask & 0x0f) << 12 | (reg & 0x0fff)); | 903 | RTL_W32(OCPAR, ((u32)mask & 0x0f) << 12 | (reg & 0x0fff)); |
| 835 | for (i = 0; i < 20; i++) { | 904 | |
| 836 | udelay(100); | 905 | return rtl_udelay_loop_wait_high(tp, &rtl_ocpar_cond, 100, 20) ? |
| 837 | if (RTL_R32(OCPAR) & OCPAR_FLAG) | 906 | RTL_R32(OCPDR) : ~0; |
| 838 | break; | ||
| 839 | } | ||
| 840 | return RTL_R32(OCPDR); | ||
| 841 | } | 907 | } |
| 842 | 908 | ||
| 843 | static void ocp_write(struct rtl8169_private *tp, u8 mask, u16 reg, u32 data) | 909 | static void ocp_write(struct rtl8169_private *tp, u8 mask, u16 reg, u32 data) |
| 844 | { | 910 | { |
| 845 | void __iomem *ioaddr = tp->mmio_addr; | 911 | void __iomem *ioaddr = tp->mmio_addr; |
| 846 | int i; | ||
| 847 | 912 | ||
| 848 | RTL_W32(OCPDR, data); | 913 | RTL_W32(OCPDR, data); |
| 849 | RTL_W32(OCPAR, OCPAR_FLAG | ((u32)mask & 0x0f) << 12 | (reg & 0x0fff)); | 914 | RTL_W32(OCPAR, OCPAR_FLAG | ((u32)mask & 0x0f) << 12 | (reg & 0x0fff)); |
| 850 | for (i = 0; i < 20; i++) { | 915 | |
| 851 | udelay(100); | 916 | rtl_udelay_loop_wait_low(tp, &rtl_ocpar_cond, 100, 20); |
| 852 | if ((RTL_R32(OCPAR) & OCPAR_FLAG) == 0) | 917 | } |
| 853 | break; | 918 | |
| 854 | } | 919 | DECLARE_RTL_COND(rtl_eriar_cond) |
| 920 | { | ||
| 921 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 922 | |||
| 923 | return RTL_R32(ERIAR) & ERIAR_FLAG; | ||
| 855 | } | 924 | } |
| 856 | 925 | ||
| 857 | static void rtl8168_oob_notify(struct rtl8169_private *tp, u8 cmd) | 926 | static void rtl8168_oob_notify(struct rtl8169_private *tp, u8 cmd) |
| 858 | { | 927 | { |
| 859 | void __iomem *ioaddr = tp->mmio_addr; | 928 | void __iomem *ioaddr = tp->mmio_addr; |
| 860 | int i; | ||
| 861 | 929 | ||
| 862 | RTL_W8(ERIDR, cmd); | 930 | RTL_W8(ERIDR, cmd); |
| 863 | RTL_W32(ERIAR, 0x800010e8); | 931 | RTL_W32(ERIAR, 0x800010e8); |
| 864 | msleep(2); | 932 | msleep(2); |
| 865 | for (i = 0; i < 5; i++) { | 933 | |
| 866 | udelay(100); | 934 | if (!rtl_udelay_loop_wait_low(tp, &rtl_eriar_cond, 100, 5)) |
| 867 | if (!(RTL_R32(ERIAR) & ERIAR_FLAG)) | 935 | return; |
| 868 | break; | ||
| 869 | } | ||
| 870 | 936 | ||
| 871 | ocp_write(tp, 0x1, 0x30, 0x00000001); | 937 | ocp_write(tp, 0x1, 0x30, 0x00000001); |
| 872 | } | 938 | } |
| @@ -880,36 +946,27 @@ static u16 rtl8168_get_ocp_reg(struct rtl8169_private *tp) | |||
| 880 | return (tp->mac_version == RTL_GIGA_MAC_VER_31) ? 0xb8 : 0x10; | 946 | return (tp->mac_version == RTL_GIGA_MAC_VER_31) ? 0xb8 : 0x10; |
| 881 | } | 947 | } |
| 882 | 948 | ||
| 883 | static void rtl8168_driver_start(struct rtl8169_private *tp) | 949 | DECLARE_RTL_COND(rtl_ocp_read_cond) |
| 884 | { | 950 | { |
| 885 | u16 reg; | 951 | u16 reg; |
| 886 | int i; | ||
| 887 | |||
| 888 | rtl8168_oob_notify(tp, OOB_CMD_DRIVER_START); | ||
| 889 | 952 | ||
| 890 | reg = rtl8168_get_ocp_reg(tp); | 953 | reg = rtl8168_get_ocp_reg(tp); |
| 891 | 954 | ||
| 892 | for (i = 0; i < 10; i++) { | 955 | return ocp_read(tp, 0x0f, reg) & 0x00000800; |
| 893 | msleep(10); | ||
| 894 | if (ocp_read(tp, 0x0f, reg) & 0x00000800) | ||
| 895 | break; | ||
| 896 | } | ||
| 897 | } | 956 | } |
| 898 | 957 | ||
| 899 | static void rtl8168_driver_stop(struct rtl8169_private *tp) | 958 | static void rtl8168_driver_start(struct rtl8169_private *tp) |
| 900 | { | 959 | { |
| 901 | u16 reg; | 960 | rtl8168_oob_notify(tp, OOB_CMD_DRIVER_START); |
| 902 | int i; | ||
| 903 | 961 | ||
| 904 | rtl8168_oob_notify(tp, OOB_CMD_DRIVER_STOP); | 962 | rtl_msleep_loop_wait_high(tp, &rtl_ocp_read_cond, 10, 10); |
| 963 | } | ||
| 905 | 964 | ||
| 906 | reg = rtl8168_get_ocp_reg(tp); | 965 | static void rtl8168_driver_stop(struct rtl8169_private *tp) |
| 966 | { | ||
| 967 | rtl8168_oob_notify(tp, OOB_CMD_DRIVER_STOP); | ||
| 907 | 968 | ||
| 908 | for (i = 0; i < 10; i++) { | 969 | rtl_msleep_loop_wait_low(tp, &rtl_ocp_read_cond, 10, 10); |
| 909 | msleep(10); | ||
| 910 | if ((ocp_read(tp, 0x0f, reg) & 0x00000800) == 0) | ||
| 911 | break; | ||
| 912 | } | ||
| 913 | } | 970 | } |
| 914 | 971 | ||
| 915 | static int r8168dp_check_dash(struct rtl8169_private *tp) | 972 | static int r8168dp_check_dash(struct rtl8169_private *tp) |
| @@ -919,22 +976,20 @@ static int r8168dp_check_dash(struct rtl8169_private *tp) | |||
| 919 | return (ocp_read(tp, 0x0f, reg) & 0x00008000) ? 1 : 0; | 976 | return (ocp_read(tp, 0x0f, reg) & 0x00008000) ? 1 : 0; |
| 920 | } | 977 | } |
| 921 | 978 | ||
| 979 | DECLARE_RTL_COND(rtl_phyar_cond) | ||
| 980 | { | ||
| 981 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 982 | |||
| 983 | return RTL_R32(PHYAR) & 0x80000000; | ||
| 984 | } | ||
| 985 | |||
| 922 | static void r8169_mdio_write(struct rtl8169_private *tp, int reg, int value) | 986 | static void r8169_mdio_write(struct rtl8169_private *tp, int reg, int value) |
| 923 | { | 987 | { |
| 924 | void __iomem *ioaddr = tp->mmio_addr; | 988 | void __iomem *ioaddr = tp->mmio_addr; |
| 925 | int i; | ||
| 926 | 989 | ||
| 927 | RTL_W32(PHYAR, 0x80000000 | (reg & 0x1f) << 16 | (value & 0xffff)); | 990 | RTL_W32(PHYAR, 0x80000000 | (reg & 0x1f) << 16 | (value & 0xffff)); |
| 928 | 991 | ||
| 929 | for (i = 20; i > 0; i--) { | 992 | rtl_udelay_loop_wait_low(tp, &rtl_phyar_cond, 25, 20); |
| 930 | /* | ||
| 931 | * Check if the RTL8169 has completed writing to the specified | ||
| 932 | * MII register. | ||
| 933 | */ | ||
| 934 | if (!(RTL_R32(PHYAR) & 0x80000000)) | ||
| 935 | break; | ||
| 936 | udelay(25); | ||
| 937 | } | ||
| 938 | /* | 993 | /* |
| 939 | * According to hardware specs a 20us delay is required after write | 994 | * According to hardware specs a 20us delay is required after write |
| 940 | * complete indication, but before sending next command. | 995 | * complete indication, but before sending next command. |
| @@ -945,21 +1000,13 @@ static void r8169_mdio_write(struct rtl8169_private *tp, int reg, int value) | |||
| 945 | static int r8169_mdio_read(struct rtl8169_private *tp, int reg) | 1000 | static int r8169_mdio_read(struct rtl8169_private *tp, int reg) |
| 946 | { | 1001 | { |
| 947 | void __iomem *ioaddr = tp->mmio_addr; | 1002 | void __iomem *ioaddr = tp->mmio_addr; |
| 948 | int i, value = -1; | 1003 | int value; |
| 949 | 1004 | ||
| 950 | RTL_W32(PHYAR, 0x0 | (reg & 0x1f) << 16); | 1005 | RTL_W32(PHYAR, 0x0 | (reg & 0x1f) << 16); |
| 951 | 1006 | ||
| 952 | for (i = 20; i > 0; i--) { | 1007 | value = rtl_udelay_loop_wait_high(tp, &rtl_phyar_cond, 25, 20) ? |
| 953 | /* | 1008 | RTL_R32(PHYAR) & 0xffff : ~0; |
| 954 | * Check if the RTL8169 has completed retrieving data from | 1009 | |
| 955 | * the specified MII register. | ||
| 956 | */ | ||
| 957 | if (RTL_R32(PHYAR) & 0x80000000) { | ||
| 958 | value = RTL_R32(PHYAR) & 0xffff; | ||
| 959 | break; | ||
| 960 | } | ||
| 961 | udelay(25); | ||
| 962 | } | ||
| 963 | /* | 1010 | /* |
| 964 | * According to hardware specs a 20us delay is required after read | 1011 | * According to hardware specs a 20us delay is required after read |
| 965 | * complete indication, but before sending next command. | 1012 | * complete indication, but before sending next command. |
| @@ -972,17 +1019,12 @@ static int r8169_mdio_read(struct rtl8169_private *tp, int reg) | |||
| 972 | static void r8168dp_1_mdio_access(struct rtl8169_private *tp, int reg, u32 data) | 1019 | static void r8168dp_1_mdio_access(struct rtl8169_private *tp, int reg, u32 data) |
| 973 | { | 1020 | { |
| 974 | void __iomem *ioaddr = tp->mmio_addr; | 1021 | void __iomem *ioaddr = tp->mmio_addr; |
| 975 | int i; | ||
| 976 | 1022 | ||
| 977 | RTL_W32(OCPDR, data | ((reg & OCPDR_REG_MASK) << OCPDR_GPHY_REG_SHIFT)); | 1023 | RTL_W32(OCPDR, data | ((reg & OCPDR_REG_MASK) << OCPDR_GPHY_REG_SHIFT)); |
| 978 | RTL_W32(OCPAR, OCPAR_GPHY_WRITE_CMD); | 1024 | RTL_W32(OCPAR, OCPAR_GPHY_WRITE_CMD); |
| 979 | RTL_W32(EPHY_RXER_NUM, 0); | 1025 | RTL_W32(EPHY_RXER_NUM, 0); |
| 980 | 1026 | ||
| 981 | for (i = 0; i < 100; i++) { | 1027 | rtl_udelay_loop_wait_low(tp, &rtl_ocpar_cond, 1000, 100); |
| 982 | mdelay(1); | ||
| 983 | if (!(RTL_R32(OCPAR) & OCPAR_FLAG)) | ||
| 984 | break; | ||
| 985 | } | ||
| 986 | } | 1028 | } |
| 987 | 1029 | ||
| 988 | static void r8168dp_1_mdio_write(struct rtl8169_private *tp, int reg, int value) | 1030 | static void r8168dp_1_mdio_write(struct rtl8169_private *tp, int reg, int value) |
| @@ -994,7 +1036,6 @@ static void r8168dp_1_mdio_write(struct rtl8169_private *tp, int reg, int value) | |||
| 994 | static int r8168dp_1_mdio_read(struct rtl8169_private *tp, int reg) | 1036 | static int r8168dp_1_mdio_read(struct rtl8169_private *tp, int reg) |
| 995 | { | 1037 | { |
| 996 | void __iomem *ioaddr = tp->mmio_addr; | 1038 | void __iomem *ioaddr = tp->mmio_addr; |
| 997 | int i; | ||
| 998 | 1039 | ||
| 999 | r8168dp_1_mdio_access(tp, reg, OCPDR_READ_CMD); | 1040 | r8168dp_1_mdio_access(tp, reg, OCPDR_READ_CMD); |
| 1000 | 1041 | ||
| @@ -1002,13 +1043,8 @@ static int r8168dp_1_mdio_read(struct rtl8169_private *tp, int reg) | |||
| 1002 | RTL_W32(OCPAR, OCPAR_GPHY_READ_CMD); | 1043 | RTL_W32(OCPAR, OCPAR_GPHY_READ_CMD); |
| 1003 | RTL_W32(EPHY_RXER_NUM, 0); | 1044 | RTL_W32(EPHY_RXER_NUM, 0); |
| 1004 | 1045 | ||
| 1005 | for (i = 0; i < 100; i++) { | 1046 | return rtl_udelay_loop_wait_high(tp, &rtl_ocpar_cond, 1000, 100) ? |
| 1006 | mdelay(1); | 1047 | RTL_R32(OCPDR) & OCPDR_DATA_MASK : ~0; |
| 1007 | if (RTL_R32(OCPAR) & OCPAR_FLAG) | ||
| 1008 | break; | ||
| 1009 | } | ||
| 1010 | |||
| 1011 | return RTL_R32(OCPDR) & OCPDR_DATA_MASK; | ||
| 1012 | } | 1048 | } |
| 1013 | 1049 | ||
| 1014 | #define R8168DP_1_MDIO_ACCESS_BIT 0x00020000 | 1050 | #define R8168DP_1_MDIO_ACCESS_BIT 0x00020000 |
| @@ -1086,74 +1122,55 @@ static int rtl_mdio_read(struct net_device *dev, int phy_id, int location) | |||
| 1086 | return rtl_readphy(tp, location); | 1122 | return rtl_readphy(tp, location); |
| 1087 | } | 1123 | } |
| 1088 | 1124 | ||
| 1125 | DECLARE_RTL_COND(rtl_ephyar_cond) | ||
| 1126 | { | ||
| 1127 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 1128 | |||
| 1129 | return RTL_R32(EPHYAR) & EPHYAR_FLAG; | ||
| 1130 | } | ||
| 1131 | |||
| 1089 | static void rtl_ephy_write(struct rtl8169_private *tp, int reg_addr, int value) | 1132 | static void rtl_ephy_write(struct rtl8169_private *tp, int reg_addr, int value) |
| 1090 | { | 1133 | { |
| 1091 | void __iomem *ioaddr = tp->mmio_addr; | 1134 | void __iomem *ioaddr = tp->mmio_addr; |
| 1092 | unsigned int i; | ||
| 1093 | 1135 | ||
| 1094 | RTL_W32(EPHYAR, EPHYAR_WRITE_CMD | (value & EPHYAR_DATA_MASK) | | 1136 | RTL_W32(EPHYAR, EPHYAR_WRITE_CMD | (value & EPHYAR_DATA_MASK) | |
| 1095 | (reg_addr & EPHYAR_REG_MASK) << EPHYAR_REG_SHIFT); | 1137 | (reg_addr & EPHYAR_REG_MASK) << EPHYAR_REG_SHIFT); |
| 1096 | 1138 | ||
| 1097 | for (i = 0; i < 100; i++) { | 1139 | rtl_udelay_loop_wait_low(tp, &rtl_ephyar_cond, 10, 100); |
| 1098 | if (!(RTL_R32(EPHYAR) & EPHYAR_FLAG)) | 1140 | |
| 1099 | break; | 1141 | udelay(10); |
| 1100 | udelay(10); | ||
| 1101 | } | ||
| 1102 | } | 1142 | } |
| 1103 | 1143 | ||
| 1104 | static u16 rtl_ephy_read(struct rtl8169_private *tp, int reg_addr) | 1144 | static u16 rtl_ephy_read(struct rtl8169_private *tp, int reg_addr) |
| 1105 | { | 1145 | { |
| 1106 | void __iomem *ioaddr = tp->mmio_addr; | 1146 | void __iomem *ioaddr = tp->mmio_addr; |
| 1107 | u16 value = 0xffff; | ||
| 1108 | unsigned int i; | ||
| 1109 | 1147 | ||
| 1110 | RTL_W32(EPHYAR, (reg_addr & EPHYAR_REG_MASK) << EPHYAR_REG_SHIFT); | 1148 | RTL_W32(EPHYAR, (reg_addr & EPHYAR_REG_MASK) << EPHYAR_REG_SHIFT); |
| 1111 | 1149 | ||
| 1112 | for (i = 0; i < 100; i++) { | 1150 | return rtl_udelay_loop_wait_high(tp, &rtl_ephyar_cond, 10, 100) ? |
| 1113 | if (RTL_R32(EPHYAR) & EPHYAR_FLAG) { | 1151 | RTL_R32(EPHYAR) & EPHYAR_DATA_MASK : ~0; |
| 1114 | value = RTL_R32(EPHYAR) & EPHYAR_DATA_MASK; | ||
| 1115 | break; | ||
| 1116 | } | ||
| 1117 | udelay(10); | ||
| 1118 | } | ||
| 1119 | |||
| 1120 | return value; | ||
| 1121 | } | 1152 | } |
| 1122 | 1153 | ||
| 1123 | static void rtl_eri_write(struct rtl8169_private *tp, int addr, u32 mask, | 1154 | static void rtl_eri_write(struct rtl8169_private *tp, int addr, u32 mask, |
| 1124 | u32 val, int type) | 1155 | u32 val, int type) |
| 1125 | { | 1156 | { |
| 1126 | void __iomem *ioaddr = tp->mmio_addr; | 1157 | void __iomem *ioaddr = tp->mmio_addr; |
| 1127 | unsigned int i; | ||
| 1128 | 1158 | ||
| 1129 | BUG_ON((addr & 3) || (mask == 0)); | 1159 | BUG_ON((addr & 3) || (mask == 0)); |
| 1130 | RTL_W32(ERIDR, val); | 1160 | RTL_W32(ERIDR, val); |
| 1131 | RTL_W32(ERIAR, ERIAR_WRITE_CMD | type | mask | addr); | 1161 | RTL_W32(ERIAR, ERIAR_WRITE_CMD | type | mask | addr); |
| 1132 | 1162 | ||
| 1133 | for (i = 0; i < 100; i++) { | 1163 | rtl_udelay_loop_wait_low(tp, &rtl_eriar_cond, 100, 100); |
| 1134 | if (!(RTL_R32(ERIAR) & ERIAR_FLAG)) | ||
| 1135 | break; | ||
| 1136 | udelay(100); | ||
| 1137 | } | ||
| 1138 | } | 1164 | } |
| 1139 | 1165 | ||
| 1140 | static u32 rtl_eri_read(struct rtl8169_private *tp, int addr, int type) | 1166 | static u32 rtl_eri_read(struct rtl8169_private *tp, int addr, int type) |
| 1141 | { | 1167 | { |
| 1142 | void __iomem *ioaddr = tp->mmio_addr; | 1168 | void __iomem *ioaddr = tp->mmio_addr; |
| 1143 | u32 value = ~0x00; | ||
| 1144 | unsigned int i; | ||
| 1145 | 1169 | ||
| 1146 | RTL_W32(ERIAR, ERIAR_READ_CMD | type | ERIAR_MASK_1111 | addr); | 1170 | RTL_W32(ERIAR, ERIAR_READ_CMD | type | ERIAR_MASK_1111 | addr); |
| 1147 | 1171 | ||
| 1148 | for (i = 0; i < 100; i++) { | 1172 | return rtl_udelay_loop_wait_high(tp, &rtl_eriar_cond, 100, 100) ? |
| 1149 | if (RTL_R32(ERIAR) & ERIAR_FLAG) { | 1173 | RTL_R32(ERIDR) : ~0; |
| 1150 | value = RTL_R32(ERIDR); | ||
| 1151 | break; | ||
| 1152 | } | ||
| 1153 | udelay(100); | ||
| 1154 | } | ||
| 1155 | |||
| 1156 | return value; | ||
| 1157 | } | 1174 | } |
| 1158 | 1175 | ||
| 1159 | static void rtl_w1w0_eri(struct rtl8169_private *tp, int addr, u32 mask, u32 p, | 1176 | static void rtl_w1w0_eri(struct rtl8169_private *tp, int addr, u32 mask, u32 p, |
| @@ -1180,23 +1197,21 @@ static void rtl_write_exgmac_batch(struct rtl8169_private *tp, | |||
| 1180 | } | 1197 | } |
| 1181 | } | 1198 | } |
| 1182 | 1199 | ||
| 1200 | DECLARE_RTL_COND(rtl_efusear_cond) | ||
| 1201 | { | ||
| 1202 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 1203 | |||
| 1204 | return RTL_R32(EFUSEAR) & EFUSEAR_FLAG; | ||
| 1205 | } | ||
| 1206 | |||
| 1183 | static u8 rtl8168d_efuse_read(struct rtl8169_private *tp, int reg_addr) | 1207 | static u8 rtl8168d_efuse_read(struct rtl8169_private *tp, int reg_addr) |
| 1184 | { | 1208 | { |
| 1185 | void __iomem *ioaddr = tp->mmio_addr; | 1209 | void __iomem *ioaddr = tp->mmio_addr; |
| 1186 | u8 value = 0xff; | ||
| 1187 | unsigned int i; | ||
| 1188 | 1210 | ||
| 1189 | RTL_W32(EFUSEAR, (reg_addr & EFUSEAR_REG_MASK) << EFUSEAR_REG_SHIFT); | 1211 | RTL_W32(EFUSEAR, (reg_addr & EFUSEAR_REG_MASK) << EFUSEAR_REG_SHIFT); |
| 1190 | 1212 | ||
| 1191 | for (i = 0; i < 300; i++) { | 1213 | return rtl_udelay_loop_wait_high(tp, &rtl_efusear_cond, 100, 300) ? |
| 1192 | if (RTL_R32(EFUSEAR) & EFUSEAR_FLAG) { | 1214 | RTL_R32(EFUSEAR) & EFUSEAR_DATA_MASK : ~0; |
| 1193 | value = RTL_R32(EFUSEAR) & EFUSEAR_DATA_MASK; | ||
| 1194 | break; | ||
| 1195 | } | ||
| 1196 | udelay(100); | ||
| 1197 | } | ||
| 1198 | |||
| 1199 | return value; | ||
| 1200 | } | 1215 | } |
| 1201 | 1216 | ||
| 1202 | static u16 rtl_get_events(struct rtl8169_private *tp) | 1217 | static u16 rtl_get_events(struct rtl8169_private *tp) |
| @@ -1803,6 +1818,13 @@ static int rtl8169_get_sset_count(struct net_device *dev, int sset) | |||
| 1803 | } | 1818 | } |
| 1804 | } | 1819 | } |
| 1805 | 1820 | ||
| 1821 | DECLARE_RTL_COND(rtl_counters_cond) | ||
| 1822 | { | ||
| 1823 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 1824 | |||
| 1825 | return RTL_R32(CounterAddrLow) & CounterDump; | ||
| 1826 | } | ||
| 1827 | |||
| 1806 | static void rtl8169_update_counters(struct net_device *dev) | 1828 | static void rtl8169_update_counters(struct net_device *dev) |
| 1807 | { | 1829 | { |
| 1808 | struct rtl8169_private *tp = netdev_priv(dev); | 1830 | struct rtl8169_private *tp = netdev_priv(dev); |
| @@ -1811,7 +1833,6 @@ static void rtl8169_update_counters(struct net_device *dev) | |||
| 1811 | struct rtl8169_counters *counters; | 1833 | struct rtl8169_counters *counters; |
| 1812 | dma_addr_t paddr; | 1834 | dma_addr_t paddr; |
| 1813 | u32 cmd; | 1835 | u32 cmd; |
| 1814 | int wait = 1000; | ||
| 1815 | 1836 | ||
| 1816 | /* | 1837 | /* |
| 1817 | * Some chips are unable to dump tally counters when the receiver | 1838 | * Some chips are unable to dump tally counters when the receiver |
| @@ -1829,13 +1850,8 @@ static void rtl8169_update_counters(struct net_device *dev) | |||
| 1829 | RTL_W32(CounterAddrLow, cmd); | 1850 | RTL_W32(CounterAddrLow, cmd); |
| 1830 | RTL_W32(CounterAddrLow, cmd | CounterDump); | 1851 | RTL_W32(CounterAddrLow, cmd | CounterDump); |
| 1831 | 1852 | ||
| 1832 | while (wait--) { | 1853 | if (rtl_udelay_loop_wait_low(tp, &rtl_counters_cond, 10, 1000)) |
| 1833 | if ((RTL_R32(CounterAddrLow) & CounterDump) == 0) { | 1854 | memcpy(&tp->counters, counters, sizeof(*counters)); |
| 1834 | memcpy(&tp->counters, counters, sizeof(*counters)); | ||
| 1835 | break; | ||
| 1836 | } | ||
| 1837 | udelay(10); | ||
| 1838 | } | ||
| 1839 | 1855 | ||
| 1840 | RTL_W32(CounterAddrLow, 0); | 1856 | RTL_W32(CounterAddrLow, 0); |
| 1841 | RTL_W32(CounterAddrHigh, 0); | 1857 | RTL_W32(CounterAddrHigh, 0); |
| @@ -3467,18 +3483,16 @@ static void rtl8169_release_board(struct pci_dev *pdev, struct net_device *dev, | |||
| 3467 | free_netdev(dev); | 3483 | free_netdev(dev); |
| 3468 | } | 3484 | } |
| 3469 | 3485 | ||
| 3486 | DECLARE_RTL_COND(rtl_phy_reset_cond) | ||
| 3487 | { | ||
| 3488 | return tp->phy_reset_pending(tp); | ||
| 3489 | } | ||
| 3490 | |||
| 3470 | static void rtl8169_phy_reset(struct net_device *dev, | 3491 | static void rtl8169_phy_reset(struct net_device *dev, |
| 3471 | struct rtl8169_private *tp) | 3492 | struct rtl8169_private *tp) |
| 3472 | { | 3493 | { |
| 3473 | unsigned int i; | ||
| 3474 | |||
| 3475 | tp->phy_reset_enable(tp); | 3494 | tp->phy_reset_enable(tp); |
| 3476 | for (i = 0; i < 100; i++) { | 3495 | rtl_msleep_loop_wait_low(tp, &rtl_phy_reset_cond, 1, 100); |
| 3477 | if (!tp->phy_reset_pending(tp)) | ||
| 3478 | return; | ||
| 3479 | msleep(1); | ||
| 3480 | } | ||
| 3481 | netif_err(tp, link, dev, "PHY reset failed\n"); | ||
| 3482 | } | 3496 | } |
| 3483 | 3497 | ||
| 3484 | static bool rtl_tbi_enabled(struct rtl8169_private *tp) | 3498 | static bool rtl_tbi_enabled(struct rtl8169_private *tp) |
| @@ -4101,20 +4115,20 @@ static void __devinit rtl_init_jumbo_ops(struct rtl8169_private *tp) | |||
| 4101 | } | 4115 | } |
| 4102 | } | 4116 | } |
| 4103 | 4117 | ||
| 4118 | DECLARE_RTL_COND(rtl_chipcmd_cond) | ||
| 4119 | { | ||
| 4120 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 4121 | |||
| 4122 | return RTL_R8(ChipCmd) & CmdReset; | ||
| 4123 | } | ||
| 4124 | |||
| 4104 | static void rtl_hw_reset(struct rtl8169_private *tp) | 4125 | static void rtl_hw_reset(struct rtl8169_private *tp) |
| 4105 | { | 4126 | { |
| 4106 | void __iomem *ioaddr = tp->mmio_addr; | 4127 | void __iomem *ioaddr = tp->mmio_addr; |
| 4107 | int i; | ||
| 4108 | 4128 | ||
| 4109 | /* Soft reset the chip. */ | ||
| 4110 | RTL_W8(ChipCmd, CmdReset); | 4129 | RTL_W8(ChipCmd, CmdReset); |
| 4111 | 4130 | ||
| 4112 | /* Check that the chip has finished the reset. */ | 4131 | rtl_udelay_loop_wait_low(tp, &rtl_chipcmd_cond, 100, 100); |
| 4113 | for (i = 0; i < 100; i++) { | ||
| 4114 | if ((RTL_R8(ChipCmd) & CmdReset) == 0) | ||
| 4115 | break; | ||
| 4116 | udelay(100); | ||
| 4117 | } | ||
| 4118 | } | 4132 | } |
| 4119 | 4133 | ||
| 4120 | static void rtl_request_uncached_firmware(struct rtl8169_private *tp) | 4134 | static void rtl_request_uncached_firmware(struct rtl8169_private *tp) |
| @@ -4168,6 +4182,20 @@ static void rtl_rx_close(struct rtl8169_private *tp) | |||
| 4168 | RTL_W32(RxConfig, RTL_R32(RxConfig) & ~RX_CONFIG_ACCEPT_MASK); | 4182 | RTL_W32(RxConfig, RTL_R32(RxConfig) & ~RX_CONFIG_ACCEPT_MASK); |
| 4169 | } | 4183 | } |
| 4170 | 4184 | ||
| 4185 | DECLARE_RTL_COND(rtl_npq_cond) | ||
| 4186 | { | ||
| 4187 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 4188 | |||
| 4189 | return RTL_R8(TxPoll) & NPQ; | ||
| 4190 | } | ||
| 4191 | |||
| 4192 | DECLARE_RTL_COND(rtl_txcfg_empty_cond) | ||
| 4193 | { | ||
| 4194 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 4195 | |||
| 4196 | return RTL_R32(TxConfig) & TXCFG_EMPTY; | ||
| 4197 | } | ||
| 4198 | |||
| 4171 | static void rtl8169_hw_reset(struct rtl8169_private *tp) | 4199 | static void rtl8169_hw_reset(struct rtl8169_private *tp) |
| 4172 | { | 4200 | { |
| 4173 | void __iomem *ioaddr = tp->mmio_addr; | 4201 | void __iomem *ioaddr = tp->mmio_addr; |
| @@ -4180,16 +4208,14 @@ static void rtl8169_hw_reset(struct rtl8169_private *tp) | |||
| 4180 | if (tp->mac_version == RTL_GIGA_MAC_VER_27 || | 4208 | if (tp->mac_version == RTL_GIGA_MAC_VER_27 || |
| 4181 | tp->mac_version == RTL_GIGA_MAC_VER_28 || | 4209 | tp->mac_version == RTL_GIGA_MAC_VER_28 || |
| 4182 | tp->mac_version == RTL_GIGA_MAC_VER_31) { | 4210 | tp->mac_version == RTL_GIGA_MAC_VER_31) { |
| 4183 | while (RTL_R8(TxPoll) & NPQ) | 4211 | rtl_udelay_loop_wait_low(tp, &rtl_npq_cond, 20, 42*42); |
| 4184 | udelay(20); | ||
| 4185 | } else if (tp->mac_version == RTL_GIGA_MAC_VER_34 || | 4212 | } else if (tp->mac_version == RTL_GIGA_MAC_VER_34 || |
| 4186 | tp->mac_version == RTL_GIGA_MAC_VER_35 || | 4213 | tp->mac_version == RTL_GIGA_MAC_VER_35 || |
| 4187 | tp->mac_version == RTL_GIGA_MAC_VER_36 || | 4214 | tp->mac_version == RTL_GIGA_MAC_VER_36 || |
| 4188 | tp->mac_version == RTL_GIGA_MAC_VER_37 || | 4215 | tp->mac_version == RTL_GIGA_MAC_VER_37 || |
| 4189 | tp->mac_version == RTL_GIGA_MAC_VER_38) { | 4216 | tp->mac_version == RTL_GIGA_MAC_VER_38) { |
| 4190 | RTL_W8(ChipCmd, RTL_R8(ChipCmd) | StopReq); | 4217 | RTL_W8(ChipCmd, RTL_R8(ChipCmd) | StopReq); |
| 4191 | while (!(RTL_R32(TxConfig) & TXCFG_EMPTY)) | 4218 | rtl_udelay_loop_wait_high(tp, &rtl_txcfg_empty_cond, 100, 666); |
| 4192 | udelay(100); | ||
| 4193 | } else { | 4219 | } else { |
| 4194 | RTL_W8(ChipCmd, RTL_R8(ChipCmd) | StopReq); | 4220 | RTL_W8(ChipCmd, RTL_R8(ChipCmd) | StopReq); |
| 4195 | udelay(100); | 4221 | udelay(100); |
| @@ -4421,77 +4447,56 @@ static void rtl_csi_access_enable_2(struct rtl8169_private *tp) | |||
| 4421 | rtl_csi_access_enable(tp, 0x27000000); | 4447 | rtl_csi_access_enable(tp, 0x27000000); |
| 4422 | } | 4448 | } |
| 4423 | 4449 | ||
| 4450 | DECLARE_RTL_COND(rtl_csiar_cond) | ||
| 4451 | { | ||
| 4452 | void __iomem *ioaddr = tp->mmio_addr; | ||
| 4453 | |||
| 4454 | return RTL_R32(CSIAR) & CSIAR_FLAG; | ||
| 4455 | } | ||
| 4456 | |||
| 4424 | static void r8169_csi_write(struct rtl8169_private *tp, int addr, int value) | 4457 | static void r8169_csi_write(struct rtl8169_private *tp, int addr, int value) |
| 4425 | { | 4458 | { |
| 4426 | void __iomem *ioaddr = tp->mmio_addr; | 4459 | void __iomem *ioaddr = tp->mmio_addr; |
| 4427 | unsigned int i; | ||
| 4428 | 4460 | ||
| 4429 | RTL_W32(CSIDR, value); | 4461 | RTL_W32(CSIDR, value); |
| 4430 | RTL_W32(CSIAR, CSIAR_WRITE_CMD | (addr & CSIAR_ADDR_MASK) | | 4462 | RTL_W32(CSIAR, CSIAR_WRITE_CMD | (addr & CSIAR_ADDR_MASK) | |
| 4431 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT); | 4463 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT); |
| 4432 | 4464 | ||
| 4433 | for (i = 0; i < 100; i++) { | 4465 | rtl_udelay_loop_wait_low(tp, &rtl_csiar_cond, 10, 100); |
| 4434 | if (!(RTL_R32(CSIAR) & CSIAR_FLAG)) | ||
| 4435 | break; | ||
| 4436 | udelay(10); | ||
| 4437 | } | ||
| 4438 | } | 4466 | } |
| 4439 | 4467 | ||
| 4440 | static u32 r8169_csi_read(struct rtl8169_private *tp, int addr) | 4468 | static u32 r8169_csi_read(struct rtl8169_private *tp, int addr) |
| 4441 | { | 4469 | { |
| 4442 | void __iomem *ioaddr = tp->mmio_addr; | 4470 | void __iomem *ioaddr = tp->mmio_addr; |
| 4443 | u32 value = ~0x00; | ||
| 4444 | unsigned int i; | ||
| 4445 | 4471 | ||
| 4446 | RTL_W32(CSIAR, (addr & CSIAR_ADDR_MASK) | | 4472 | RTL_W32(CSIAR, (addr & CSIAR_ADDR_MASK) | |
| 4447 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT); | 4473 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT); |
| 4448 | 4474 | ||
| 4449 | for (i = 0; i < 100; i++) { | 4475 | return rtl_udelay_loop_wait_high(tp, &rtl_csiar_cond, 10, 100) ? |
| 4450 | if (RTL_R32(CSIAR) & CSIAR_FLAG) { | 4476 | RTL_R32(CSIDR) : ~0; |
| 4451 | value = RTL_R32(CSIDR); | ||
| 4452 | break; | ||
| 4453 | } | ||
| 4454 | udelay(10); | ||
| 4455 | } | ||
| 4456 | |||
| 4457 | return value; | ||
| 4458 | } | 4477 | } |
| 4459 | 4478 | ||
| 4460 | static void r8402_csi_write(struct rtl8169_private *tp, int addr, int value) | 4479 | static void r8402_csi_write(struct rtl8169_private *tp, int addr, int value) |
| 4461 | { | 4480 | { |
| 4462 | void __iomem *ioaddr = tp->mmio_addr; | 4481 | void __iomem *ioaddr = tp->mmio_addr; |
| 4463 | unsigned int i; | ||
| 4464 | 4482 | ||
| 4465 | RTL_W32(CSIDR, value); | 4483 | RTL_W32(CSIDR, value); |
| 4466 | RTL_W32(CSIAR, CSIAR_WRITE_CMD | (addr & CSIAR_ADDR_MASK) | | 4484 | RTL_W32(CSIAR, CSIAR_WRITE_CMD | (addr & CSIAR_ADDR_MASK) | |
| 4467 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT | | 4485 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT | |
| 4468 | CSIAR_FUNC_NIC); | 4486 | CSIAR_FUNC_NIC); |
| 4469 | 4487 | ||
| 4470 | for (i = 0; i < 100; i++) { | 4488 | rtl_udelay_loop_wait_low(tp, &rtl_csiar_cond, 10, 100); |
| 4471 | if (!(RTL_R32(CSIAR) & CSIAR_FLAG)) | ||
| 4472 | break; | ||
| 4473 | udelay(10); | ||
| 4474 | } | ||
| 4475 | } | 4489 | } |
| 4476 | 4490 | ||
| 4477 | static u32 r8402_csi_read(struct rtl8169_private *tp, int addr) | 4491 | static u32 r8402_csi_read(struct rtl8169_private *tp, int addr) |
| 4478 | { | 4492 | { |
| 4479 | void __iomem *ioaddr = tp->mmio_addr; | 4493 | void __iomem *ioaddr = tp->mmio_addr; |
| 4480 | u32 value = ~0x00; | ||
| 4481 | unsigned int i; | ||
| 4482 | 4494 | ||
| 4483 | RTL_W32(CSIAR, (addr & CSIAR_ADDR_MASK) | CSIAR_FUNC_NIC | | 4495 | RTL_W32(CSIAR, (addr & CSIAR_ADDR_MASK) | CSIAR_FUNC_NIC | |
| 4484 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT); | 4496 | CSIAR_BYTE_ENABLE << CSIAR_BYTE_ENABLE_SHIFT); |
| 4485 | 4497 | ||
| 4486 | for (i = 0; i < 100; i++) { | 4498 | return rtl_udelay_loop_wait_high(tp, &rtl_csiar_cond, 10, 100) ? |
| 4487 | if (RTL_R32(CSIAR) & CSIAR_FLAG) { | 4499 | RTL_R32(CSIDR) : ~0; |
| 4488 | value = RTL_R32(CSIDR); | ||
| 4489 | break; | ||
| 4490 | } | ||
| 4491 | udelay(10); | ||
| 4492 | } | ||
| 4493 | |||
| 4494 | return value; | ||
| 4495 | } | 4500 | } |
| 4496 | 4501 | ||
| 4497 | static void __devinit rtl_init_csi_ops(struct rtl8169_private *tp) | 4502 | static void __devinit rtl_init_csi_ops(struct rtl8169_private *tp) |
