aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/e1000e
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/e1000e')
-rw-r--r--drivers/net/e1000e/lib.c62
1 files changed, 18 insertions, 44 deletions
diff --git a/drivers/net/e1000e/lib.c b/drivers/net/e1000e/lib.c
index ac2f34e1836..18a4f5902f3 100644
--- a/drivers/net/e1000e/lib.c
+++ b/drivers/net/e1000e/lib.c
@@ -159,41 +159,6 @@ void e1000e_rar_set(struct e1000_hw *hw, u8 *addr, u32 index)
159} 159}
160 160
161/** 161/**
162 * e1000_mta_set - Set multicast filter table address
163 * @hw: pointer to the HW structure
164 * @hash_value: determines the MTA register and bit to set
165 *
166 * The multicast table address is a register array of 32-bit registers.
167 * The hash_value is used to determine what register the bit is in, the
168 * current value is read, the new bit is OR'd in and the new value is
169 * written back into the register.
170 **/
171static void e1000_mta_set(struct e1000_hw *hw, u32 hash_value)
172{
173 u32 hash_bit, hash_reg, mta;
174
175 /*
176 * The MTA is a register array of 32-bit registers. It is
177 * treated like an array of (32*mta_reg_count) bits. We want to
178 * set bit BitArray[hash_value]. So we figure out what register
179 * the bit is in, read it, OR in the new bit, then write
180 * back the new value. The (hw->mac.mta_reg_count - 1) serves as a
181 * mask to bits 31:5 of the hash value which gives us the
182 * register we're modifying. The hash bit within that register
183 * is determined by the lower 5 bits of the hash value.
184 */
185 hash_reg = (hash_value >> 5) & (hw->mac.mta_reg_count - 1);
186 hash_bit = hash_value & 0x1F;
187
188 mta = E1000_READ_REG_ARRAY(hw, E1000_MTA, hash_reg);
189
190 mta |= (1 << hash_bit);
191
192 E1000_WRITE_REG_ARRAY(hw, E1000_MTA, hash_reg, mta);
193 e1e_flush();
194}
195
196/**
197 * e1000_hash_mc_addr - Generate a multicast hash value 162 * e1000_hash_mc_addr - Generate a multicast hash value
198 * @hw: pointer to the HW structure 163 * @hw: pointer to the HW structure
199 * @mc_addr: pointer to a multicast address 164 * @mc_addr: pointer to a multicast address
@@ -281,8 +246,13 @@ void e1000e_update_mc_addr_list_generic(struct e1000_hw *hw,
281 u8 *mc_addr_list, u32 mc_addr_count, 246 u8 *mc_addr_list, u32 mc_addr_count,
282 u32 rar_used_count, u32 rar_count) 247 u32 rar_used_count, u32 rar_count)
283{ 248{
284 u32 hash_value;
285 u32 i; 249 u32 i;
250 u32 *mcarray = kzalloc(hw->mac.mta_reg_count * sizeof(u32), GFP_ATOMIC);
251
252 if (!mcarray) {
253 printk(KERN_ERR "multicast array memory allocation failed\n");
254 return;
255 }
286 256
287 /* 257 /*
288 * Load the first set of multicast addresses into the exact 258 * Load the first set of multicast addresses into the exact
@@ -302,20 +272,24 @@ void e1000e_update_mc_addr_list_generic(struct e1000_hw *hw,
302 } 272 }
303 } 273 }
304 274
305 /* Clear the old settings from the MTA */
306 hw_dbg(hw, "Clearing MTA\n");
307 for (i = 0; i < hw->mac.mta_reg_count; i++) {
308 E1000_WRITE_REG_ARRAY(hw, E1000_MTA, i, 0);
309 e1e_flush();
310 }
311
312 /* Load any remaining multicast addresses into the hash table. */ 275 /* Load any remaining multicast addresses into the hash table. */
313 for (; mc_addr_count > 0; mc_addr_count--) { 276 for (; mc_addr_count > 0; mc_addr_count--) {
277 u32 hash_value, hash_reg, hash_bit, mta;
314 hash_value = e1000_hash_mc_addr(hw, mc_addr_list); 278 hash_value = e1000_hash_mc_addr(hw, mc_addr_list);
315 hw_dbg(hw, "Hash value = 0x%03X\n", hash_value); 279 hw_dbg(hw, "Hash value = 0x%03X\n", hash_value);
316 e1000_mta_set(hw, hash_value); 280 hash_reg = (hash_value >> 5) & (hw->mac.mta_reg_count - 1);
281 hash_bit = hash_value & 0x1F;
282 mta = (1 << hash_bit);
283 mcarray[hash_reg] |= mta;
317 mc_addr_list += ETH_ALEN; 284 mc_addr_list += ETH_ALEN;
318 } 285 }
286
287 /* write the hash table completely */
288 for (i = 0; i < hw->mac.mta_reg_count; i++)
289 E1000_WRITE_REG_ARRAY(hw, E1000_MTA, i, mcarray[i]);
290
291 e1e_flush();
292 kfree(mcarray);
319} 293}
320 294
321/** 295/**