mvebu: add linux 4.9 support
[openwrt/openwrt.git] / target / linux / mvebu / patches-4.9 / 410-net-phy-allow-settings-table-to-support-more-than-32.patch
1 From: Russell King <rmk+kernel@armlinux.org.uk>
2 Date: Thu, 5 Jan 2017 16:32:14 +0000
3 Subject: [PATCH] net: phy: allow settings table to support more than 32
4 link modes
5
6 Allow the phy settings table to support more than 32 link modes by
7 switching to the ethtool link mode bit number representation, rather
8 than storing the mask. This will allow phylink and other ethtool
9 code to share the settings table to look up settings.
10
11 Signed-off-by: Russell King <rmk+kernel@armlinux.org.uk>
12 ---
13
14 --- a/drivers/net/phy/phy.c
15 +++ b/drivers/net/phy/phy.c
16 @@ -175,7 +175,7 @@ static inline int phy_aneg_done(struct p
17 struct phy_setting {
18 int speed;
19 int duplex;
20 - u32 setting;
21 + int bit;
22 };
23
24 /* A mapping of all SUPPORTED settings to speed/duplex. This table
25 @@ -185,57 +185,57 @@ static const struct phy_setting settings
26 {
27 .speed = SPEED_10000,
28 .duplex = DUPLEX_FULL,
29 - .setting = SUPPORTED_10000baseKR_Full,
30 + .bit = ETHTOOL_LINK_MODE_10000baseKR_Full_BIT,
31 },
32 {
33 .speed = SPEED_10000,
34 .duplex = DUPLEX_FULL,
35 - .setting = SUPPORTED_10000baseKX4_Full,
36 + .bit = ETHTOOL_LINK_MODE_10000baseKX4_Full_BIT,
37 },
38 {
39 .speed = SPEED_10000,
40 .duplex = DUPLEX_FULL,
41 - .setting = SUPPORTED_10000baseT_Full,
42 + .bit = ETHTOOL_LINK_MODE_10000baseT_Full_BIT,
43 },
44 {
45 .speed = SPEED_2500,
46 .duplex = DUPLEX_FULL,
47 - .setting = SUPPORTED_2500baseX_Full,
48 + .bit = ETHTOOL_LINK_MODE_2500baseX_Full_BIT,
49 },
50 {
51 .speed = SPEED_1000,
52 .duplex = DUPLEX_FULL,
53 - .setting = SUPPORTED_1000baseKX_Full,
54 + .bit = ETHTOOL_LINK_MODE_1000baseKX_Full_BIT,
55 },
56 {
57 .speed = SPEED_1000,
58 .duplex = DUPLEX_FULL,
59 - .setting = SUPPORTED_1000baseT_Full,
60 + .bit = ETHTOOL_LINK_MODE_1000baseT_Full_BIT,
61 },
62 {
63 .speed = SPEED_1000,
64 .duplex = DUPLEX_HALF,
65 - .setting = SUPPORTED_1000baseT_Half,
66 + .bit = ETHTOOL_LINK_MODE_1000baseT_Half_BIT,
67 },
68 {
69 .speed = SPEED_100,
70 .duplex = DUPLEX_FULL,
71 - .setting = SUPPORTED_100baseT_Full,
72 + .bit = ETHTOOL_LINK_MODE_100baseT_Full_BIT,
73 },
74 {
75 .speed = SPEED_100,
76 .duplex = DUPLEX_HALF,
77 - .setting = SUPPORTED_100baseT_Half,
78 + .bit = ETHTOOL_LINK_MODE_100baseT_Half_BIT,
79 },
80 {
81 .speed = SPEED_10,
82 .duplex = DUPLEX_FULL,
83 - .setting = SUPPORTED_10baseT_Full,
84 + .bit = ETHTOOL_LINK_MODE_10baseT_Full_BIT,
85 },
86 {
87 .speed = SPEED_10,
88 .duplex = DUPLEX_HALF,
89 - .setting = SUPPORTED_10baseT_Half,
90 + .bit = ETHTOOL_LINK_MODE_10baseT_Half_BIT,
91 },
92 };
93
94 @@ -243,7 +243,8 @@ static const struct phy_setting settings
95 * phy_lookup_setting - lookup a PHY setting
96 * @speed: speed to match
97 * @duplex: duplex to match
98 - * @feature: allowed link modes
99 + * @mask: allowed link modes
100 + * @maxbit: bit size of link modes
101 * @exact: an exact match is required
102 *
103 * Search the settings array for a setting that matches the speed and
104 @@ -257,13 +258,14 @@ static const struct phy_setting settings
105 * they all fail, %NULL will be returned.
106 */
107 static const struct phy_setting *
108 -phy_lookup_setting(int speed, int duplex, u32 features, bool exact)
109 +phy_lookup_setting(int speed, int duplex, const unsigned long *mask,
110 + size_t maxbit, bool exact)
111 {
112 const struct phy_setting *p, *match = NULL, *last = NULL;
113 int i;
114
115 for (i = 0, p = settings; i < ARRAY_SIZE(settings); i++, p++) {
116 - if (p->setting & features) {
117 + if (p->bit < maxbit && test_bit(p->bit, mask)) {
118 last = p;
119 if (p->speed == speed && p->duplex == duplex) {
120 /* Exact match for speed and duplex */
121 @@ -302,7 +304,9 @@ phy_lookup_setting(int speed, int duplex
122 static const struct phy_setting *
123 phy_find_valid(int speed, int duplex, u32 supported)
124 {
125 - return phy_lookup_setting(speed, duplex, supported, false);
126 + unsigned long mask = supported;
127 +
128 + return phy_lookup_setting(speed, duplex, &mask, BITS_PER_LONG, false);
129 }
130
131 /**
132 @@ -316,7 +320,9 @@ phy_find_valid(int speed, int duplex, u3
133 */
134 static inline bool phy_check_valid(int speed, int duplex, u32 features)
135 {
136 - return !!phy_lookup_setting(speed, duplex, features, true);
137 + unsigned long mask = features;
138 +
139 + return !!phy_lookup_setting(speed, duplex, &mask, BITS_PER_LONG, true);
140 }
141
142 /**