瀏覽代碼

Merge branch 'upstream-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jgarzik/netdev-2.6

* 'upstream-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/jgarzik/netdev-2.6: (31 commits)
  Replace cpmac fix
  dl2k: the rest
  dl2k: MSCR, MSSR, ESR, PHY_SCR fixes
  dl2k: BMSR fixes
  dl2k: ANAR, ANLPAR fixes
  dl2k: BMCR_t fixes
  3c574, 3c515 bitfields abuse
  sbni endian fixes
  wan/lmc bitfields fixes
  dscc4 endian fixes
  S2io: Fixed synchronization between scheduling of napi with card reset and close
  atl1: fix frame length bug
  Documentation: add a guideline for hard_start_xmit method
  Revert "sky2: remove check for PCI wakeup setting from BIOS"
  e1000e Kconfig: remove ref to nonexistant docs
  bonding: Don't hold lock when calling rtnl_unlock
  bonding: fix lock ordering for rtnl and bonding_rwsem
  bonding: Fix up parameter parsing
  bonding: release slaves when master removed via sysfs
  bonding: fix locking during alb failover and slave removal
  ...
Linus Torvalds 17 年之前
父節點
當前提交
8b2d1833a2

+ 4 - 1
Documentation/networking/driver.txt

@@ -61,7 +61,10 @@ Transmit path guidelines:
 2) Do not forget to update netdev->trans_start to jiffies after
 2) Do not forget to update netdev->trans_start to jiffies after
    each new tx packet is given to the hardware.
    each new tx packet is given to the hardware.
 
 
-3) Do not forget that once you return 0 from your hard_start_xmit
+3) A hard_start_xmit method must not modify the shared parts of a
+   cloned SKB.
+
+4) Do not forget that once you return 0 from your hard_start_xmit
    method, it is your driver's responsibility to free up the SKB
    method, it is your driver's responsibility to free up the SKB
    and in some finite amount of time.
    and in some finite amount of time.
 
 

+ 31 - 29
drivers/net/3c515.c

@@ -243,14 +243,16 @@ enum eeprom_offset {
 enum Window3 {			/* Window 3: MAC/config bits. */
 enum Window3 {			/* Window 3: MAC/config bits. */
 	Wn3_Config = 0, Wn3_MAC_Ctrl = 6, Wn3_Options = 8,
 	Wn3_Config = 0, Wn3_MAC_Ctrl = 6, Wn3_Options = 8,
 };
 };
-union wn3_config {
-	int i;
-	struct w3_config_fields {
-		unsigned int ram_size:3, ram_width:1, ram_speed:2, rom_size:2;
-		int pad8:8;
-		unsigned int ram_split:2, pad18:2, xcvr:3, pad21:1, autoselect:1;
-		int pad24:7;
-	} u;
+enum wn3_config {
+	Ram_size = 7,
+	Ram_width = 8,
+	Ram_speed = 0x30,
+	Rom_size = 0xc0,
+	Ram_split_shift = 16,
+	Ram_split = 3 << Ram_split_shift,
+	Xcvr_shift = 20,
+	Xcvr = 7 << Xcvr_shift,
+	Autoselect = 0x1000000,
 };
 };
 
 
 enum Window4 {
 enum Window4 {
@@ -614,7 +616,7 @@ static int corkscrew_setup(struct net_device *dev, int ioaddr,
 	/* Read the station address from the EEPROM. */
 	/* Read the station address from the EEPROM. */
 	EL3WINDOW(0);
 	EL3WINDOW(0);
 	for (i = 0; i < 0x18; i++) {
 	for (i = 0; i < 0x18; i++) {
-		short *phys_addr = (short *) dev->dev_addr;
+		__be16 *phys_addr = (__be16 *) dev->dev_addr;
 		int timer;
 		int timer;
 		outw(EEPROM_Read + i, ioaddr + Wn0EepromCmd);
 		outw(EEPROM_Read + i, ioaddr + Wn0EepromCmd);
 		/* Pause for at least 162 us. for the read to take place. */
 		/* Pause for at least 162 us. for the read to take place. */
@@ -646,22 +648,22 @@ static int corkscrew_setup(struct net_device *dev, int ioaddr,
 
 
 	{
 	{
 		char *ram_split[] = { "5:3", "3:1", "1:1", "3:5" };
 		char *ram_split[] = { "5:3", "3:1", "1:1", "3:5" };
-		union wn3_config config;
+		__u32 config;
 		EL3WINDOW(3);
 		EL3WINDOW(3);
 		vp->available_media = inw(ioaddr + Wn3_Options);
 		vp->available_media = inw(ioaddr + Wn3_Options);
-		config.i = inl(ioaddr + Wn3_Config);
+		config = inl(ioaddr + Wn3_Config);
 		if (corkscrew_debug > 1)
 		if (corkscrew_debug > 1)
 			printk(KERN_INFO "  Internal config register is %4.4x, transceivers %#x.\n",
 			printk(KERN_INFO "  Internal config register is %4.4x, transceivers %#x.\n",
-				config.i, inw(ioaddr + Wn3_Options));
+				config, inw(ioaddr + Wn3_Options));
 		printk(KERN_INFO "  %dK %s-wide RAM %s Rx:Tx split, %s%s interface.\n",
 		printk(KERN_INFO "  %dK %s-wide RAM %s Rx:Tx split, %s%s interface.\n",
-			8 << config.u.ram_size,
-			config.u.ram_width ? "word" : "byte",
-			ram_split[config.u.ram_split],
-			config.u.autoselect ? "autoselect/" : "",
-			media_tbl[config.u.xcvr].name);
-		dev->if_port = config.u.xcvr;
-		vp->default_media = config.u.xcvr;
-		vp->autoselect = config.u.autoselect;
+			8 << config & Ram_size,
+			config & Ram_width ? "word" : "byte",
+			ram_split[(config & Ram_split) >> Ram_split_shift],
+			config & Autoselect ? "autoselect/" : "",
+			media_tbl[(config & Xcvr) >> Xcvr_shift].name);
+		vp->default_media = (config & Xcvr) >> Xcvr_shift;
+		vp->autoselect = config & Autoselect ? 1 : 0;
+		dev->if_port = vp->default_media;
 	}
 	}
 	if (vp->media_override != 7) {
 	if (vp->media_override != 7) {
 		printk(KERN_INFO "  Media override to transceiver type %d (%s).\n",
 		printk(KERN_INFO "  Media override to transceiver type %d (%s).\n",
@@ -694,14 +696,14 @@ static int corkscrew_open(struct net_device *dev)
 {
 {
 	int ioaddr = dev->base_addr;
 	int ioaddr = dev->base_addr;
 	struct corkscrew_private *vp = netdev_priv(dev);
 	struct corkscrew_private *vp = netdev_priv(dev);
-	union wn3_config config;
+	__u32 config;
 	int i;
 	int i;
 
 
 	/* Before initializing select the active media port. */
 	/* Before initializing select the active media port. */
 	EL3WINDOW(3);
 	EL3WINDOW(3);
 	if (vp->full_duplex)
 	if (vp->full_duplex)
 		outb(0x20, ioaddr + Wn3_MAC_Ctrl);	/* Set the full-duplex bit. */
 		outb(0x20, ioaddr + Wn3_MAC_Ctrl);	/* Set the full-duplex bit. */
-	config.i = inl(ioaddr + Wn3_Config);
+	config = inl(ioaddr + Wn3_Config);
 
 
 	if (vp->media_override != 7) {
 	if (vp->media_override != 7) {
 		if (corkscrew_debug > 1)
 		if (corkscrew_debug > 1)
@@ -727,12 +729,12 @@ static int corkscrew_open(struct net_device *dev)
 	} else
 	} else
 		dev->if_port = vp->default_media;
 		dev->if_port = vp->default_media;
 
 
-	config.u.xcvr = dev->if_port;
-	outl(config.i, ioaddr + Wn3_Config);
+	config = (config & ~Xcvr) | (dev->if_port << Xcvr_shift);
+	outl(config, ioaddr + Wn3_Config);
 
 
 	if (corkscrew_debug > 1) {
 	if (corkscrew_debug > 1) {
 		printk("%s: corkscrew_open() InternalConfig %8.8x.\n",
 		printk("%s: corkscrew_open() InternalConfig %8.8x.\n",
-		       dev->name, config.i);
+		       dev->name, config);
 	}
 	}
 
 
 	outw(TxReset, ioaddr + EL3_CMD);
 	outw(TxReset, ioaddr + EL3_CMD);
@@ -901,7 +903,7 @@ static void corkscrew_timer(unsigned long data)
 			ok = 1;
 			ok = 1;
 		}
 		}
 		if (!ok) {
 		if (!ok) {
-			union wn3_config config;
+			__u32 config;
 
 
 			do {
 			do {
 				dev->if_port =
 				dev->if_port =
@@ -928,9 +930,9 @@ static void corkscrew_timer(unsigned long data)
 			     ioaddr + Wn4_Media);
 			     ioaddr + Wn4_Media);
 
 
 			EL3WINDOW(3);
 			EL3WINDOW(3);
-			config.i = inl(ioaddr + Wn3_Config);
-			config.u.xcvr = dev->if_port;
-			outl(config.i, ioaddr + Wn3_Config);
+			config = inl(ioaddr + Wn3_Config);
+			config = (config & ~Xcvr) | (dev->if_port << Xcvr_shift);
+			outl(config, ioaddr + Wn3_Config);
 
 
 			outw(dev->if_port == 3 ? StartCoax : StopCoax,
 			outw(dev->if_port == 3 ? StartCoax : StopCoax,
 			     ioaddr + EL3_CMD);
 			     ioaddr + EL3_CMD);

+ 0 - 3
drivers/net/Kconfig

@@ -1976,9 +1976,6 @@ config E1000E
 
 
 	  <http://support.intel.com>
 	  <http://support.intel.com>
 
 
-	  More specific information on configuring the driver is in
-	  <file:Documentation/networking/e1000e.txt>.
-
 	  To compile this driver as a module, choose M here. The module
 	  To compile this driver as a module, choose M here. The module
 	  will be called e1000e.
 	  will be called e1000e.
 
 

+ 4 - 4
drivers/net/atl1/atl1_main.c

@@ -120,7 +120,7 @@ static int __devinit atl1_sw_init(struct atl1_adapter *adapter)
 	struct atl1_hw *hw = &adapter->hw;
 	struct atl1_hw *hw = &adapter->hw;
 	struct net_device *netdev = adapter->netdev;
 	struct net_device *netdev = adapter->netdev;
 
 
-	hw->max_frame_size = netdev->mtu + ETH_HLEN + ETH_FCS_LEN;
+	hw->max_frame_size = netdev->mtu + ETH_HLEN + ETH_FCS_LEN + VLAN_HLEN;
 	hw->min_frame_size = ETH_ZLEN + ETH_FCS_LEN;
 	hw->min_frame_size = ETH_ZLEN + ETH_FCS_LEN;
 
 
 	adapter->wol = 0;
 	adapter->wol = 0;
@@ -688,7 +688,7 @@ static int atl1_change_mtu(struct net_device *netdev, int new_mtu)
 {
 {
 	struct atl1_adapter *adapter = netdev_priv(netdev);
 	struct atl1_adapter *adapter = netdev_priv(netdev);
 	int old_mtu = netdev->mtu;
 	int old_mtu = netdev->mtu;
-	int max_frame = new_mtu + ETH_HLEN + ETH_FCS_LEN;
+	int max_frame = new_mtu + ETH_HLEN + ETH_FCS_LEN + VLAN_HLEN;
 
 
 	if ((max_frame < ETH_ZLEN + ETH_FCS_LEN) ||
 	if ((max_frame < ETH_ZLEN + ETH_FCS_LEN) ||
 	    (max_frame > MAX_JUMBO_FRAME_SIZE)) {
 	    (max_frame > MAX_JUMBO_FRAME_SIZE)) {
@@ -853,8 +853,8 @@ static u32 atl1_configure(struct atl1_adapter *adapter)
 	/* set Interrupt Clear Timer */
 	/* set Interrupt Clear Timer */
 	iowrite16(adapter->ict, hw->hw_addr + REG_CMBDISDMA_TIMER);
 	iowrite16(adapter->ict, hw->hw_addr + REG_CMBDISDMA_TIMER);
 
 
-	/* set MTU, 4 : VLAN */
-	iowrite32(hw->max_frame_size + 4, hw->hw_addr + REG_MTU);
+	/* set max frame size hw will accept */
+	iowrite32(hw->max_frame_size, hw->hw_addr + REG_MTU);
 
 
 	/* jumbo size & rrd retirement timer */
 	/* jumbo size & rrd retirement timer */
 	value = (((u32) hw->rx_jumbo_th & RXQ_JMBOSZ_TH_MASK)
 	value = (((u32) hw->rx_jumbo_th & RXQ_JMBOSZ_TH_MASK)

+ 14 - 9
drivers/net/bonding/bond_alb.c

@@ -979,7 +979,7 @@ static void alb_swap_mac_addr(struct bonding *bond, struct slave *slave1, struct
 /*
 /*
  * Send learning packets after MAC address swap.
  * Send learning packets after MAC address swap.
  *
  *
- * Called with RTNL and bond->lock held for read.
+ * Called with RTNL and no other locks
  */
  */
 static void alb_fasten_mac_swap(struct bonding *bond, struct slave *slave1,
 static void alb_fasten_mac_swap(struct bonding *bond, struct slave *slave1,
 				struct slave *slave2)
 				struct slave *slave2)
@@ -987,6 +987,8 @@ static void alb_fasten_mac_swap(struct bonding *bond, struct slave *slave1,
 	int slaves_state_differ = (SLAVE_IS_OK(slave1) != SLAVE_IS_OK(slave2));
 	int slaves_state_differ = (SLAVE_IS_OK(slave1) != SLAVE_IS_OK(slave2));
 	struct slave *disabled_slave = NULL;
 	struct slave *disabled_slave = NULL;
 
 
+	ASSERT_RTNL();
+
 	/* fasten the change in the switch */
 	/* fasten the change in the switch */
 	if (SLAVE_IS_OK(slave1)) {
 	if (SLAVE_IS_OK(slave1)) {
 		alb_send_learning_packets(slave1, slave1->dev->dev_addr);
 		alb_send_learning_packets(slave1, slave1->dev->dev_addr);
@@ -1031,7 +1033,7 @@ static void alb_fasten_mac_swap(struct bonding *bond, struct slave *slave1,
  * a slave that has @slave's permanet address as its current address.
  * a slave that has @slave's permanet address as its current address.
  * We'll make sure that that slave no longer uses @slave's permanent address.
  * We'll make sure that that slave no longer uses @slave's permanent address.
  *
  *
- * Caller must hold bond lock
+ * Caller must hold RTNL and no other locks
  */
  */
 static void alb_change_hw_addr_on_detach(struct bonding *bond, struct slave *slave)
 static void alb_change_hw_addr_on_detach(struct bonding *bond, struct slave *slave)
 {
 {
@@ -1542,7 +1544,12 @@ int bond_alb_init_slave(struct bonding *bond, struct slave *slave)
 	return 0;
 	return 0;
 }
 }
 
 
-/* Caller must hold bond lock for write */
+/*
+ * Remove slave from tlb and rlb hash tables, and fix up MAC addresses
+ * if necessary.
+ *
+ * Caller must hold RTNL and no other locks
+ */
 void bond_alb_deinit_slave(struct bonding *bond, struct slave *slave)
 void bond_alb_deinit_slave(struct bonding *bond, struct slave *slave)
 {
 {
 	if (bond->slave_cnt > 1) {
 	if (bond->slave_cnt > 1) {
@@ -1601,9 +1608,6 @@ void bond_alb_handle_active_change(struct bonding *bond, struct slave *new_slave
 	struct slave *swap_slave;
 	struct slave *swap_slave;
 	int i;
 	int i;
 
 
-	if (new_slave)
-		ASSERT_RTNL();
-
 	if (bond->curr_active_slave == new_slave) {
 	if (bond->curr_active_slave == new_slave) {
 		return;
 		return;
 	}
 	}
@@ -1649,6 +1653,8 @@ void bond_alb_handle_active_change(struct bonding *bond, struct slave *new_slave
 	write_unlock_bh(&bond->curr_slave_lock);
 	write_unlock_bh(&bond->curr_slave_lock);
 	read_unlock(&bond->lock);
 	read_unlock(&bond->lock);
 
 
+	ASSERT_RTNL();
+
 	/* curr_active_slave must be set before calling alb_swap_mac_addr */
 	/* curr_active_slave must be set before calling alb_swap_mac_addr */
 	if (swap_slave) {
 	if (swap_slave) {
 		/* swap mac address */
 		/* swap mac address */
@@ -1659,12 +1665,11 @@ void bond_alb_handle_active_change(struct bonding *bond, struct slave *new_slave
 				       bond->alb_info.rlb_enabled);
 				       bond->alb_info.rlb_enabled);
 	}
 	}
 
 
-	read_lock(&bond->lock);
-
 	if (swap_slave) {
 	if (swap_slave) {
 		alb_fasten_mac_swap(bond, swap_slave, new_slave);
 		alb_fasten_mac_swap(bond, swap_slave, new_slave);
+		read_lock(&bond->lock);
 	} else {
 	} else {
-		/* fasten bond mac on new current slave */
+		read_lock(&bond->lock);
 		alb_send_learning_packets(new_slave, bond->dev->dev_addr);
 		alb_send_learning_packets(new_slave, bond->dev->dev_addr);
 	}
 	}
 
 

+ 47 - 17
drivers/net/bonding/bond_main.c

@@ -1746,7 +1746,9 @@ int bond_release(struct net_device *bond_dev, struct net_device *slave_dev)
 		 * has been cleared (if our_slave == old_current),
 		 * has been cleared (if our_slave == old_current),
 		 * but before a new active slave is selected.
 		 * but before a new active slave is selected.
 		 */
 		 */
+		write_unlock_bh(&bond->lock);
 		bond_alb_deinit_slave(bond, slave);
 		bond_alb_deinit_slave(bond, slave);
+		write_lock_bh(&bond->lock);
 	}
 	}
 
 
 	if (oldcurrent == slave) {
 	if (oldcurrent == slave) {
@@ -1905,6 +1907,12 @@ static int bond_release_all(struct net_device *bond_dev)
 		slave_dev = slave->dev;
 		slave_dev = slave->dev;
 		bond_detach_slave(bond, slave);
 		bond_detach_slave(bond, slave);
 
 
+		/* now that the slave is detached, unlock and perform
+		 * all the undo steps that should not be called from
+		 * within a lock.
+		 */
+		write_unlock_bh(&bond->lock);
+
 		if ((bond->params.mode == BOND_MODE_TLB) ||
 		if ((bond->params.mode == BOND_MODE_TLB) ||
 		    (bond->params.mode == BOND_MODE_ALB)) {
 		    (bond->params.mode == BOND_MODE_ALB)) {
 			/* must be called only after the slave
 			/* must be called only after the slave
@@ -1915,12 +1923,6 @@ static int bond_release_all(struct net_device *bond_dev)
 
 
 		bond_compute_features(bond);
 		bond_compute_features(bond);
 
 
-		/* now that the slave is detached, unlock and perform
-		 * all the undo steps that should not be called from
-		 * within a lock.
-		 */
-		write_unlock_bh(&bond->lock);
-
 		bond_destroy_slave_symlinks(bond_dev, slave_dev);
 		bond_destroy_slave_symlinks(bond_dev, slave_dev);
 		bond_del_vlans_from_slave(bond, slave_dev);
 		bond_del_vlans_from_slave(bond, slave_dev);
 
 
@@ -2384,7 +2386,9 @@ void bond_mii_monitor(struct work_struct *work)
 		rtnl_lock();
 		rtnl_lock();
 		read_lock(&bond->lock);
 		read_lock(&bond->lock);
 		__bond_mii_monitor(bond, 1);
 		__bond_mii_monitor(bond, 1);
-		rtnl_unlock();
+		read_unlock(&bond->lock);
+		rtnl_unlock();	/* might sleep, hold no other locks */
+		read_lock(&bond->lock);
 	}
 	}
 
 
 	delay = ((bond->params.miimon * HZ) / 1000) ? : 1;
 	delay = ((bond->params.miimon * HZ) / 1000) ? : 1;
@@ -3399,9 +3403,7 @@ static int bond_master_netdev_event(unsigned long event, struct net_device *bond
 	case NETDEV_CHANGENAME:
 	case NETDEV_CHANGENAME:
 		return bond_event_changename(event_bond);
 		return bond_event_changename(event_bond);
 	case NETDEV_UNREGISTER:
 	case NETDEV_UNREGISTER:
-		/*
-		 * TODO: remove a bond from the list?
-		 */
+		bond_release_all(event_bond->dev);
 		break;
 		break;
 	default:
 	default:
 		break;
 		break;
@@ -4540,18 +4542,27 @@ static void bond_free_all(void)
 
 
 /*
 /*
  * Convert string input module parms.  Accept either the
  * Convert string input module parms.  Accept either the
- * number of the mode or its string name.
+ * number of the mode or its string name.  A bit complicated because
+ * some mode names are substrings of other names, and calls from sysfs
+ * may have whitespace in the name (trailing newlines, for example).
  */
  */
-int bond_parse_parm(char *mode_arg, struct bond_parm_tbl *tbl)
+int bond_parse_parm(const char *buf, struct bond_parm_tbl *tbl)
 {
 {
-	int i;
+	int mode = -1, i, rv;
+	char modestr[BOND_MAX_MODENAME_LEN + 1] = { 0, };
+
+	rv = sscanf(buf, "%d", &mode);
+	if (!rv) {
+		rv = sscanf(buf, "%20s", modestr);
+		if (!rv)
+			return -1;
+	}
 
 
 	for (i = 0; tbl[i].modename; i++) {
 	for (i = 0; tbl[i].modename; i++) {
-		if ((isdigit(*mode_arg) &&
-		     tbl[i].mode == simple_strtol(mode_arg, NULL, 0)) ||
-		    (strcmp(mode_arg, tbl[i].modename) == 0)) {
+		if (mode == tbl[i].mode)
+			return tbl[i].mode;
+		if (strcmp(modestr, tbl[i].modename) == 0)
 			return tbl[i].mode;
 			return tbl[i].mode;
-		}
 	}
 	}
 
 
 	return -1;
 	return -1;
@@ -4865,9 +4876,22 @@ static struct lock_class_key bonding_netdev_xmit_lock_key;
 int bond_create(char *name, struct bond_params *params, struct bonding **newbond)
 int bond_create(char *name, struct bond_params *params, struct bonding **newbond)
 {
 {
 	struct net_device *bond_dev;
 	struct net_device *bond_dev;
+	struct bonding *bond, *nxt;
 	int res;
 	int res;
 
 
 	rtnl_lock();
 	rtnl_lock();
+	down_write(&bonding_rwsem);
+
+	/* Check to see if the bond already exists. */
+	list_for_each_entry_safe(bond, nxt, &bond_dev_list, bond_list)
+		if (strnicmp(bond->dev->name, name, IFNAMSIZ) == 0) {
+			printk(KERN_ERR DRV_NAME
+			       ": cannot add bond %s; it already exists\n",
+			       name);
+			res = -EPERM;
+			goto out_rtnl;
+		}
+
 	bond_dev = alloc_netdev(sizeof(struct bonding), name ? name : "",
 	bond_dev = alloc_netdev(sizeof(struct bonding), name ? name : "",
 				ether_setup);
 				ether_setup);
 	if (!bond_dev) {
 	if (!bond_dev) {
@@ -4906,10 +4930,12 @@ int bond_create(char *name, struct bond_params *params, struct bonding **newbond
 
 
 	netif_carrier_off(bond_dev);
 	netif_carrier_off(bond_dev);
 
 
+	up_write(&bonding_rwsem);
 	rtnl_unlock(); /* allows sysfs registration of net device */
 	rtnl_unlock(); /* allows sysfs registration of net device */
 	res = bond_create_sysfs_entry(bond_dev->priv);
 	res = bond_create_sysfs_entry(bond_dev->priv);
 	if (res < 0) {
 	if (res < 0) {
 		rtnl_lock();
 		rtnl_lock();
+		down_write(&bonding_rwsem);
 		goto out_bond;
 		goto out_bond;
 	}
 	}
 
 
@@ -4920,6 +4946,7 @@ out_bond:
 out_netdev:
 out_netdev:
 	free_netdev(bond_dev);
 	free_netdev(bond_dev);
 out_rtnl:
 out_rtnl:
+	up_write(&bonding_rwsem);
 	rtnl_unlock();
 	rtnl_unlock();
 	return res;
 	return res;
 }
 }
@@ -4940,6 +4967,9 @@ static int __init bonding_init(void)
 #ifdef CONFIG_PROC_FS
 #ifdef CONFIG_PROC_FS
 	bond_create_proc_dir();
 	bond_create_proc_dir();
 #endif
 #endif
+
+	init_rwsem(&bonding_rwsem);
+
 	for (i = 0; i < max_bonds; i++) {
 	for (i = 0; i < max_bonds; i++) {
 		res = bond_create(NULL, &bonding_defaults, NULL);
 		res = bond_create(NULL, &bonding_defaults, NULL);
 		if (res)
 		if (res)

+ 30 - 36
drivers/net/bonding/bond_sysfs.c

@@ -109,11 +109,10 @@ static ssize_t bonding_store_bonds(struct class *cls, const char *buffer, size_t
 {
 {
 	char command[IFNAMSIZ + 1] = {0, };
 	char command[IFNAMSIZ + 1] = {0, };
 	char *ifname;
 	char *ifname;
-	int res = count;
+	int rv, res = count;
 	struct bonding *bond;
 	struct bonding *bond;
 	struct bonding *nxt;
 	struct bonding *nxt;
 
 
-	down_write(&(bonding_rwsem));
 	sscanf(buffer, "%16s", command); /* IFNAMSIZ*/
 	sscanf(buffer, "%16s", command); /* IFNAMSIZ*/
 	ifname = command + 1;
 	ifname = command + 1;
 	if ((strlen(command) <= 1) ||
 	if ((strlen(command) <= 1) ||
@@ -121,39 +120,28 @@ static ssize_t bonding_store_bonds(struct class *cls, const char *buffer, size_t
 		goto err_no_cmd;
 		goto err_no_cmd;
 
 
 	if (command[0] == '+') {
 	if (command[0] == '+') {
-
-		/* Check to see if the bond already exists. */
-		list_for_each_entry_safe(bond, nxt, &bond_dev_list, bond_list)
-			if (strnicmp(bond->dev->name, ifname, IFNAMSIZ) == 0) {
-				printk(KERN_ERR DRV_NAME
-					": cannot add bond %s; it already exists\n",
-					ifname);
-				res = -EPERM;
-				goto out;
-			}
-
 		printk(KERN_INFO DRV_NAME
 		printk(KERN_INFO DRV_NAME
 			": %s is being created...\n", ifname);
 			": %s is being created...\n", ifname);
-		if (bond_create(ifname, &bonding_defaults, &bond)) {
-			printk(KERN_INFO DRV_NAME
-			": %s interface already exists. Bond creation failed.\n",
-			ifname);
-			res = -EPERM;
+		rv = bond_create(ifname, &bonding_defaults, &bond);
+		if (rv) {
+			printk(KERN_INFO DRV_NAME ": Bond creation failed.\n");
+			res = rv;
 		}
 		}
 		goto out;
 		goto out;
 	}
 	}
 
 
 	if (command[0] == '-') {
 	if (command[0] == '-') {
+		rtnl_lock();
+		down_write(&bonding_rwsem);
+
 		list_for_each_entry_safe(bond, nxt, &bond_dev_list, bond_list)
 		list_for_each_entry_safe(bond, nxt, &bond_dev_list, bond_list)
 			if (strnicmp(bond->dev->name, ifname, IFNAMSIZ) == 0) {
 			if (strnicmp(bond->dev->name, ifname, IFNAMSIZ) == 0) {
-				rtnl_lock();
 				/* check the ref count on the bond's kobject.
 				/* check the ref count on the bond's kobject.
 				 * If it's > expected, then there's a file open,
 				 * If it's > expected, then there's a file open,
 				 * and we have to fail.
 				 * and we have to fail.
 				 */
 				 */
 				if (atomic_read(&bond->dev->dev.kobj.kref.refcount)
 				if (atomic_read(&bond->dev->dev.kobj.kref.refcount)
 							> expected_refcount){
 							> expected_refcount){
-					rtnl_unlock();
 					printk(KERN_INFO DRV_NAME
 					printk(KERN_INFO DRV_NAME
 						": Unable remove bond %s due to open references.\n",
 						": Unable remove bond %s due to open references.\n",
 						ifname);
 						ifname);
@@ -164,6 +152,7 @@ static ssize_t bonding_store_bonds(struct class *cls, const char *buffer, size_t
 					": %s is being deleted...\n",
 					": %s is being deleted...\n",
 					bond->dev->name);
 					bond->dev->name);
 				bond_destroy(bond);
 				bond_destroy(bond);
+				up_write(&bonding_rwsem);
 				rtnl_unlock();
 				rtnl_unlock();
 				goto out;
 				goto out;
 			}
 			}
@@ -171,6 +160,8 @@ static ssize_t bonding_store_bonds(struct class *cls, const char *buffer, size_t
 		printk(KERN_ERR DRV_NAME
 		printk(KERN_ERR DRV_NAME
 			": unable to delete non-existent bond %s\n", ifname);
 			": unable to delete non-existent bond %s\n", ifname);
 		res = -ENODEV;
 		res = -ENODEV;
+		up_write(&bonding_rwsem);
+		rtnl_unlock();
 		goto out;
 		goto out;
 	}
 	}
 
 
@@ -183,7 +174,6 @@ err_no_cmd:
 	 * get called forever, which is bad.
 	 * get called forever, which is bad.
 	 */
 	 */
 out:
 out:
-	up_write(&(bonding_rwsem));
 	return res;
 	return res;
 }
 }
 /* class attribute for bond_masters file.  This ends up in /sys/class/net */
 /* class attribute for bond_masters file.  This ends up in /sys/class/net */
@@ -271,6 +261,9 @@ static ssize_t bonding_store_slaves(struct device *d,
 
 
 	/* Note:  We can't hold bond->lock here, as bond_create grabs it. */
 	/* Note:  We can't hold bond->lock here, as bond_create grabs it. */
 
 
+	rtnl_lock();
+	down_write(&(bonding_rwsem));
+
 	sscanf(buffer, "%16s", command); /* IFNAMSIZ*/
 	sscanf(buffer, "%16s", command); /* IFNAMSIZ*/
 	ifname = command + 1;
 	ifname = command + 1;
 	if ((strlen(command) <= 1) ||
 	if ((strlen(command) <= 1) ||
@@ -336,12 +329,10 @@ static ssize_t bonding_store_slaves(struct device *d,
 				dev->mtu = bond->dev->mtu;
 				dev->mtu = bond->dev->mtu;
 			}
 			}
 		}
 		}
-		rtnl_lock();
 		res = bond_enslave(bond->dev, dev);
 		res = bond_enslave(bond->dev, dev);
 		bond_for_each_slave(bond, slave, i)
 		bond_for_each_slave(bond, slave, i)
 			if (strnicmp(slave->dev->name, ifname, IFNAMSIZ) == 0)
 			if (strnicmp(slave->dev->name, ifname, IFNAMSIZ) == 0)
 				slave->original_mtu = original_mtu;
 				slave->original_mtu = original_mtu;
-		rtnl_unlock();
 		if (res) {
 		if (res) {
 			ret = res;
 			ret = res;
 		}
 		}
@@ -359,12 +350,10 @@ static ssize_t bonding_store_slaves(struct device *d,
 		if (dev) {
 		if (dev) {
 			printk(KERN_INFO DRV_NAME ": %s: Removing slave %s\n",
 			printk(KERN_INFO DRV_NAME ": %s: Removing slave %s\n",
 				bond->dev->name, dev->name);
 				bond->dev->name, dev->name);
-			rtnl_lock();
 			if (bond->setup_by_slave)
 			if (bond->setup_by_slave)
 				res = bond_release_and_destroy(bond->dev, dev);
 				res = bond_release_and_destroy(bond->dev, dev);
 			else
 			else
 				res = bond_release(bond->dev, dev);
 				res = bond_release(bond->dev, dev);
-			rtnl_unlock();
 			if (res) {
 			if (res) {
 				ret = res;
 				ret = res;
 				goto out;
 				goto out;
@@ -389,6 +378,8 @@ err_no_cmd:
 	ret = -EPERM;
 	ret = -EPERM;
 
 
 out:
 out:
+	up_write(&(bonding_rwsem));
+	rtnl_unlock();
 	return ret;
 	return ret;
 }
 }
 
 
@@ -423,7 +414,7 @@ static ssize_t bonding_store_mode(struct device *d,
 		goto out;
 		goto out;
 	}
 	}
 
 
-	new_value = bond_parse_parm((char *)buf, bond_mode_tbl);
+	new_value = bond_parse_parm(buf, bond_mode_tbl);
 	if (new_value < 0)  {
 	if (new_value < 0)  {
 		printk(KERN_ERR DRV_NAME
 		printk(KERN_ERR DRV_NAME
 		       ": %s: Ignoring invalid mode value %.*s.\n",
 		       ": %s: Ignoring invalid mode value %.*s.\n",
@@ -478,7 +469,7 @@ static ssize_t bonding_store_xmit_hash(struct device *d,
 		goto out;
 		goto out;
 	}
 	}
 
 
-	new_value = bond_parse_parm((char *)buf, xmit_hashtype_tbl);
+	new_value = bond_parse_parm(buf, xmit_hashtype_tbl);
 	if (new_value < 0)  {
 	if (new_value < 0)  {
 		printk(KERN_ERR DRV_NAME
 		printk(KERN_ERR DRV_NAME
 		       ": %s: Ignoring invalid xmit hash policy value %.*s.\n",
 		       ": %s: Ignoring invalid xmit hash policy value %.*s.\n",
@@ -518,7 +509,7 @@ static ssize_t bonding_store_arp_validate(struct device *d,
 	int new_value;
 	int new_value;
 	struct bonding *bond = to_bond(d);
 	struct bonding *bond = to_bond(d);
 
 
-	new_value = bond_parse_parm((char *)buf, arp_validate_tbl);
+	new_value = bond_parse_parm(buf, arp_validate_tbl);
 	if (new_value < 0) {
 	if (new_value < 0) {
 		printk(KERN_ERR DRV_NAME
 		printk(KERN_ERR DRV_NAME
 		       ": %s: Ignoring invalid arp_validate value %s\n",
 		       ": %s: Ignoring invalid arp_validate value %s\n",
@@ -941,7 +932,7 @@ static ssize_t bonding_store_lacp(struct device *d,
 		goto out;
 		goto out;
 	}
 	}
 
 
-	new_value = bond_parse_parm((char *)buf, bond_lacp_tbl);
+	new_value = bond_parse_parm(buf, bond_lacp_tbl);
 
 
 	if ((new_value == 1) || (new_value == 0)) {
 	if ((new_value == 1) || (new_value == 0)) {
 		bond->params.lacp_fast = new_value;
 		bond->params.lacp_fast = new_value;
@@ -1075,7 +1066,10 @@ static ssize_t bonding_store_primary(struct device *d,
 	struct slave *slave;
 	struct slave *slave;
 	struct bonding *bond = to_bond(d);
 	struct bonding *bond = to_bond(d);
 
 
-	write_lock_bh(&bond->lock);
+	rtnl_lock();
+	read_lock(&bond->lock);
+	write_lock_bh(&bond->curr_slave_lock);
+
 	if (!USES_PRIMARY(bond->params.mode)) {
 	if (!USES_PRIMARY(bond->params.mode)) {
 		printk(KERN_INFO DRV_NAME
 		printk(KERN_INFO DRV_NAME
 		       ": %s: Unable to set primary slave; %s is in mode %d\n",
 		       ": %s: Unable to set primary slave; %s is in mode %d\n",
@@ -1109,8 +1103,8 @@ static ssize_t bonding_store_primary(struct device *d,
 		}
 		}
 	}
 	}
 out:
 out:
-	write_unlock_bh(&bond->lock);
-
+	write_unlock_bh(&bond->curr_slave_lock);
+	read_unlock(&bond->lock);
 	rtnl_unlock();
 	rtnl_unlock();
 
 
 	return count;
 	return count;
@@ -1190,7 +1184,8 @@ static ssize_t bonding_store_active_slave(struct device *d,
 	struct bonding *bond = to_bond(d);
 	struct bonding *bond = to_bond(d);
 
 
 	rtnl_lock();
 	rtnl_lock();
-	write_lock_bh(&bond->lock);
+	read_lock(&bond->lock);
+	write_lock_bh(&bond->curr_slave_lock);
 
 
 	if (!USES_PRIMARY(bond->params.mode)) {
 	if (!USES_PRIMARY(bond->params.mode)) {
 		printk(KERN_INFO DRV_NAME
 		printk(KERN_INFO DRV_NAME
@@ -1247,7 +1242,8 @@ static ssize_t bonding_store_active_slave(struct device *d,
 		}
 		}
 	}
 	}
 out:
 out:
-	write_unlock_bh(&bond->lock);
+	write_unlock_bh(&bond->curr_slave_lock);
+	read_unlock(&bond->lock);
 	rtnl_unlock();
 	rtnl_unlock();
 
 
 	return count;
 	return count;
@@ -1418,8 +1414,6 @@ int bond_create_sysfs(void)
 	int ret = 0;
 	int ret = 0;
 	struct bonding *firstbond;
 	struct bonding *firstbond;
 
 
-	init_rwsem(&bonding_rwsem);
-
 	/* get the netdev class pointer */
 	/* get the netdev class pointer */
 	firstbond = container_of(bond_dev_list.next, struct bonding, bond_list);
 	firstbond = container_of(bond_dev_list.next, struct bonding, bond_list);
 	if (!firstbond)
 	if (!firstbond)

+ 3 - 1
drivers/net/bonding/bonding.h

@@ -141,6 +141,8 @@ struct bond_parm_tbl {
 	int mode;
 	int mode;
 };
 };
 
 
+#define BOND_MAX_MODENAME_LEN 20
+
 struct vlan_entry {
 struct vlan_entry {
 	struct list_head vlan_list;
 	struct list_head vlan_list;
 	__be32 vlan_ip;
 	__be32 vlan_ip;
@@ -314,7 +316,7 @@ void bond_mii_monitor(struct work_struct *);
 void bond_loadbalance_arp_mon(struct work_struct *);
 void bond_loadbalance_arp_mon(struct work_struct *);
 void bond_activebackup_arp_mon(struct work_struct *);
 void bond_activebackup_arp_mon(struct work_struct *);
 void bond_set_mode_ops(struct bonding *bond, int mode);
 void bond_set_mode_ops(struct bonding *bond, int mode);
-int bond_parse_parm(char *mode_arg, struct bond_parm_tbl *tbl);
+int bond_parse_parm(const char *mode_arg, struct bond_parm_tbl *tbl);
 void bond_select_active_slave(struct bonding *bond);
 void bond_select_active_slave(struct bonding *bond);
 void bond_change_active_slave(struct bonding *bond, struct slave *new_active);
 void bond_change_active_slave(struct bonding *bond, struct slave *new_active);
 void bond_register_arp(struct bonding *);
 void bond_register_arp(struct bonding *);

+ 1 - 1
drivers/net/cpmac.c

@@ -459,7 +459,7 @@ static int cpmac_start_xmit(struct sk_buff *skb, struct net_device *dev)
 		return NETDEV_TX_OK;
 		return NETDEV_TX_OK;
 
 
 	len = max(skb->len, ETH_ZLEN);
 	len = max(skb->len, ETH_ZLEN);
-	queue = skb->queue_mapping;
+	queue = skb_get_queue_mapping(skb);
 #ifdef CONFIG_NETDEVICES_MULTIQUEUE
 #ifdef CONFIG_NETDEVICES_MULTIQUEUE
 	netif_stop_subqueue(dev, queue);
 	netif_stop_subqueue(dev, queue);
 #else
 #else

+ 107 - 108
drivers/net/dl2k.c

@@ -1316,9 +1316,10 @@ rio_ioctl (struct net_device *dev, struct ifreq *rq, int cmd)
 			    ("%02x:cur:%08x next:%08x status:%08x frag1:%08x frag0:%08x",
 			    ("%02x:cur:%08x next:%08x status:%08x frag1:%08x frag0:%08x",
 			     i,
 			     i,
 			     (u32) (np->tx_ring_dma + i * sizeof (*desc)),
 			     (u32) (np->tx_ring_dma + i * sizeof (*desc)),
-			     (u32) desc->next_desc,
-			     (u32) desc->status, (u32) (desc->fraginfo >> 32),
-			     (u32) desc->fraginfo);
+			     (u32)le64_to_cpu(desc->next_desc),
+			     (u32)le64_to_cpu(desc->status),
+			     (u32)(le64_to_cpu(desc->fraginfo) >> 32),
+			     (u32)le64_to_cpu(desc->fraginfo));
 			printk ("\n");
 			printk ("\n");
 		}
 		}
 		printk ("\n");
 		printk ("\n");
@@ -1435,7 +1436,7 @@ mii_write (struct net_device *dev, int phy_addr, int reg_num, u16 data)
 static int
 static int
 mii_wait_link (struct net_device *dev, int wait)
 mii_wait_link (struct net_device *dev, int wait)
 {
 {
-	BMSR_t bmsr;
+	__u16 bmsr;
 	int phy_addr;
 	int phy_addr;
 	struct netdev_private *np;
 	struct netdev_private *np;
 
 
@@ -1443,8 +1444,8 @@ mii_wait_link (struct net_device *dev, int wait)
 	phy_addr = np->phy_addr;
 	phy_addr = np->phy_addr;
 
 
 	do {
 	do {
-		bmsr.image = mii_read (dev, phy_addr, MII_BMSR);
-		if (bmsr.bits.link_status)
+		bmsr = mii_read (dev, phy_addr, MII_BMSR);
+		if (bmsr & MII_BMSR_LINK_STATUS)
 			return 0;
 			return 0;
 		mdelay (1);
 		mdelay (1);
 	} while (--wait > 0);
 	} while (--wait > 0);
@@ -1453,70 +1454,72 @@ mii_wait_link (struct net_device *dev, int wait)
 static int
 static int
 mii_get_media (struct net_device *dev)
 mii_get_media (struct net_device *dev)
 {
 {
-	ANAR_t negotiate;
-	BMSR_t bmsr;
-	BMCR_t bmcr;
-	MSCR_t mscr;
-	MSSR_t mssr;
+	__u16 negotiate;
+	__u16 bmsr;
+	__u16 mscr;
+	__u16 mssr;
 	int phy_addr;
 	int phy_addr;
 	struct netdev_private *np;
 	struct netdev_private *np;
 
 
 	np = netdev_priv(dev);
 	np = netdev_priv(dev);
 	phy_addr = np->phy_addr;
 	phy_addr = np->phy_addr;
 
 
-	bmsr.image = mii_read (dev, phy_addr, MII_BMSR);
+	bmsr = mii_read (dev, phy_addr, MII_BMSR);
 	if (np->an_enable) {
 	if (np->an_enable) {
-		if (!bmsr.bits.an_complete) {
+		if (!(bmsr & MII_BMSR_AN_COMPLETE)) {
 			/* Auto-Negotiation not completed */
 			/* Auto-Negotiation not completed */
 			return -1;
 			return -1;
 		}
 		}
-		negotiate.image = mii_read (dev, phy_addr, MII_ANAR) &
+		negotiate = mii_read (dev, phy_addr, MII_ANAR) &
 			mii_read (dev, phy_addr, MII_ANLPAR);
 			mii_read (dev, phy_addr, MII_ANLPAR);
-		mscr.image = mii_read (dev, phy_addr, MII_MSCR);
-		mssr.image = mii_read (dev, phy_addr, MII_MSSR);
-		if (mscr.bits.media_1000BT_FD & mssr.bits.lp_1000BT_FD) {
+		mscr = mii_read (dev, phy_addr, MII_MSCR);
+		mssr = mii_read (dev, phy_addr, MII_MSSR);
+		if (mscr & MII_MSCR_1000BT_FD && mssr & MII_MSSR_LP_1000BT_FD) {
 			np->speed = 1000;
 			np->speed = 1000;
 			np->full_duplex = 1;
 			np->full_duplex = 1;
 			printk (KERN_INFO "Auto 1000 Mbps, Full duplex\n");
 			printk (KERN_INFO "Auto 1000 Mbps, Full duplex\n");
-		} else if (mscr.bits.media_1000BT_HD & mssr.bits.lp_1000BT_HD) {
+		} else if (mscr & MII_MSCR_1000BT_HD && mssr & MII_MSSR_LP_1000BT_HD) {
 			np->speed = 1000;
 			np->speed = 1000;
 			np->full_duplex = 0;
 			np->full_duplex = 0;
 			printk (KERN_INFO "Auto 1000 Mbps, Half duplex\n");
 			printk (KERN_INFO "Auto 1000 Mbps, Half duplex\n");
-		} else if (negotiate.bits.media_100BX_FD) {
+		} else if (negotiate & MII_ANAR_100BX_FD) {
 			np->speed = 100;
 			np->speed = 100;
 			np->full_duplex = 1;
 			np->full_duplex = 1;
 			printk (KERN_INFO "Auto 100 Mbps, Full duplex\n");
 			printk (KERN_INFO "Auto 100 Mbps, Full duplex\n");
-		} else if (negotiate.bits.media_100BX_HD) {
+		} else if (negotiate & MII_ANAR_100BX_HD) {
 			np->speed = 100;
 			np->speed = 100;
 			np->full_duplex = 0;
 			np->full_duplex = 0;
 			printk (KERN_INFO "Auto 100 Mbps, Half duplex\n");
 			printk (KERN_INFO "Auto 100 Mbps, Half duplex\n");
-		} else if (negotiate.bits.media_10BT_FD) {
+		} else if (negotiate & MII_ANAR_10BT_FD) {
 			np->speed = 10;
 			np->speed = 10;
 			np->full_duplex = 1;
 			np->full_duplex = 1;
 			printk (KERN_INFO "Auto 10 Mbps, Full duplex\n");
 			printk (KERN_INFO "Auto 10 Mbps, Full duplex\n");
-		} else if (negotiate.bits.media_10BT_HD) {
+		} else if (negotiate & MII_ANAR_10BT_HD) {
 			np->speed = 10;
 			np->speed = 10;
 			np->full_duplex = 0;
 			np->full_duplex = 0;
 			printk (KERN_INFO "Auto 10 Mbps, Half duplex\n");
 			printk (KERN_INFO "Auto 10 Mbps, Half duplex\n");
 		}
 		}
-		if (negotiate.bits.pause) {
+		if (negotiate & MII_ANAR_PAUSE) {
 			np->tx_flow &= 1;
 			np->tx_flow &= 1;
 			np->rx_flow &= 1;
 			np->rx_flow &= 1;
-		} else if (negotiate.bits.asymmetric) {
+		} else if (negotiate & MII_ANAR_ASYMMETRIC) {
 			np->tx_flow = 0;
 			np->tx_flow = 0;
 			np->rx_flow &= 1;
 			np->rx_flow &= 1;
 		}
 		}
 		/* else tx_flow, rx_flow = user select  */
 		/* else tx_flow, rx_flow = user select  */
 	} else {
 	} else {
-		bmcr.image = mii_read (dev, phy_addr, MII_BMCR);
-		if (bmcr.bits.speed100 == 1 && bmcr.bits.speed1000 == 0) {
+		__u16 bmcr = mii_read (dev, phy_addr, MII_BMCR);
+		switch (bmcr & (MII_BMCR_SPEED_100 | MII_BMCR_SPEED_1000)) {
+		case MII_BMCR_SPEED_1000:
+			printk (KERN_INFO "Operating at 1000 Mbps, ");
+			break;
+		case MII_BMCR_SPEED_100:
 			printk (KERN_INFO "Operating at 100 Mbps, ");
 			printk (KERN_INFO "Operating at 100 Mbps, ");
-		} else if (bmcr.bits.speed100 == 0 && bmcr.bits.speed1000 == 0) {
+			break;
+		case 0:
 			printk (KERN_INFO "Operating at 10 Mbps, ");
 			printk (KERN_INFO "Operating at 10 Mbps, ");
-		} else if (bmcr.bits.speed100 == 0 && bmcr.bits.speed1000 == 1) {
-			printk (KERN_INFO "Operating at 1000 Mbps, ");
 		}
 		}
-		if (bmcr.bits.duplex_mode) {
+		if (bmcr & MII_BMCR_DUPLEX_MODE) {
 			printk ("Full duplex\n");
 			printk ("Full duplex\n");
 		} else {
 		} else {
 			printk ("Half duplex\n");
 			printk ("Half duplex\n");
@@ -1537,10 +1540,10 @@ mii_get_media (struct net_device *dev)
 static int
 static int
 mii_set_media (struct net_device *dev)
 mii_set_media (struct net_device *dev)
 {
 {
-	PHY_SCR_t pscr;
-	BMCR_t bmcr;
-	BMSR_t bmsr;
-	ANAR_t anar;
+	__u16 pscr;
+	__u16 bmcr;
+	__u16 bmsr;
+	__u16 anar;
 	int phy_addr;
 	int phy_addr;
 	struct netdev_private *np;
 	struct netdev_private *np;
 	np = netdev_priv(dev);
 	np = netdev_priv(dev);
@@ -1549,76 +1552,77 @@ mii_set_media (struct net_device *dev)
 	/* Does user set speed? */
 	/* Does user set speed? */
 	if (np->an_enable) {
 	if (np->an_enable) {
 		/* Advertise capabilities */
 		/* Advertise capabilities */
-		bmsr.image = mii_read (dev, phy_addr, MII_BMSR);
-		anar.image = mii_read (dev, phy_addr, MII_ANAR);
-		anar.bits.media_100BX_FD = bmsr.bits.media_100BX_FD;
-		anar.bits.media_100BX_HD = bmsr.bits.media_100BX_HD;
-		anar.bits.media_100BT4 = bmsr.bits.media_100BT4;
-		anar.bits.media_10BT_FD = bmsr.bits.media_10BT_FD;
-		anar.bits.media_10BT_HD = bmsr.bits.media_10BT_HD;
-		anar.bits.pause = 1;
-		anar.bits.asymmetric = 1;
-		mii_write (dev, phy_addr, MII_ANAR, anar.image);
+		bmsr = mii_read (dev, phy_addr, MII_BMSR);
+		anar = mii_read (dev, phy_addr, MII_ANAR) &
+			     ~MII_ANAR_100BX_FD &
+			     ~MII_ANAR_100BX_HD &
+			     ~MII_ANAR_100BT4 &
+			     ~MII_ANAR_10BT_FD &
+			     ~MII_ANAR_10BT_HD;
+		if (bmsr & MII_BMSR_100BX_FD)
+			anar |= MII_ANAR_100BX_FD;
+		if (bmsr & MII_BMSR_100BX_HD)
+			anar |= MII_ANAR_100BX_HD;
+		if (bmsr & MII_BMSR_100BT4)
+			anar |= MII_ANAR_100BT4;
+		if (bmsr & MII_BMSR_10BT_FD)
+			anar |= MII_ANAR_10BT_FD;
+		if (bmsr & MII_BMSR_10BT_HD)
+			anar |= MII_ANAR_10BT_HD;
+		anar |= MII_ANAR_PAUSE | MII_ANAR_ASYMMETRIC;
+		mii_write (dev, phy_addr, MII_ANAR, anar);
 
 
 		/* Enable Auto crossover */
 		/* Enable Auto crossover */
-		pscr.image = mii_read (dev, phy_addr, MII_PHY_SCR);
-		pscr.bits.mdi_crossover_mode = 3;	/* 11'b */
-		mii_write (dev, phy_addr, MII_PHY_SCR, pscr.image);
+		pscr = mii_read (dev, phy_addr, MII_PHY_SCR);
+		pscr |= 3 << 5;	/* 11'b */
+		mii_write (dev, phy_addr, MII_PHY_SCR, pscr);
 
 
 		/* Soft reset PHY */
 		/* Soft reset PHY */
 		mii_write (dev, phy_addr, MII_BMCR, MII_BMCR_RESET);
 		mii_write (dev, phy_addr, MII_BMCR, MII_BMCR_RESET);
-		bmcr.image = 0;
-		bmcr.bits.an_enable = 1;
-		bmcr.bits.restart_an = 1;
-		bmcr.bits.reset = 1;
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		bmcr = MII_BMCR_AN_ENABLE | MII_BMCR_RESTART_AN | MII_BMCR_RESET;
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 		mdelay(1);
 		mdelay(1);
 	} else {
 	} else {
 		/* Force speed setting */
 		/* Force speed setting */
 		/* 1) Disable Auto crossover */
 		/* 1) Disable Auto crossover */
-		pscr.image = mii_read (dev, phy_addr, MII_PHY_SCR);
-		pscr.bits.mdi_crossover_mode = 0;
-		mii_write (dev, phy_addr, MII_PHY_SCR, pscr.image);
+		pscr = mii_read (dev, phy_addr, MII_PHY_SCR);
+		pscr &= ~(3 << 5);
+		mii_write (dev, phy_addr, MII_PHY_SCR, pscr);
 
 
 		/* 2) PHY Reset */
 		/* 2) PHY Reset */
-		bmcr.image = mii_read (dev, phy_addr, MII_BMCR);
-		bmcr.bits.reset = 1;
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		bmcr = mii_read (dev, phy_addr, MII_BMCR);
+		bmcr |= MII_BMCR_RESET;
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 
 
 		/* 3) Power Down */
 		/* 3) Power Down */
-		bmcr.image = 0x1940;	/* must be 0x1940 */
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		bmcr = 0x1940;	/* must be 0x1940 */
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 		mdelay (100);	/* wait a certain time */
 		mdelay (100);	/* wait a certain time */
 
 
 		/* 4) Advertise nothing */
 		/* 4) Advertise nothing */
 		mii_write (dev, phy_addr, MII_ANAR, 0);
 		mii_write (dev, phy_addr, MII_ANAR, 0);
 
 
 		/* 5) Set media and Power Up */
 		/* 5) Set media and Power Up */
-		bmcr.image = 0;
-		bmcr.bits.power_down = 1;
+		bmcr = MII_BMCR_POWER_DOWN;
 		if (np->speed == 100) {
 		if (np->speed == 100) {
-			bmcr.bits.speed100 = 1;
-			bmcr.bits.speed1000 = 0;
+			bmcr |= MII_BMCR_SPEED_100;
 			printk (KERN_INFO "Manual 100 Mbps, ");
 			printk (KERN_INFO "Manual 100 Mbps, ");
 		} else if (np->speed == 10) {
 		} else if (np->speed == 10) {
-			bmcr.bits.speed100 = 0;
-			bmcr.bits.speed1000 = 0;
 			printk (KERN_INFO "Manual 10 Mbps, ");
 			printk (KERN_INFO "Manual 10 Mbps, ");
 		}
 		}
 		if (np->full_duplex) {
 		if (np->full_duplex) {
-			bmcr.bits.duplex_mode = 1;
+			bmcr |= MII_BMCR_DUPLEX_MODE;
 			printk ("Full duplex\n");
 			printk ("Full duplex\n");
 		} else {
 		} else {
-			bmcr.bits.duplex_mode = 0;
 			printk ("Half duplex\n");
 			printk ("Half duplex\n");
 		}
 		}
 #if 0
 #if 0
 		/* Set 1000BaseT Master/Slave setting */
 		/* Set 1000BaseT Master/Slave setting */
-		mscr.image = mii_read (dev, phy_addr, MII_MSCR);
-		mscr.bits.cfg_enable = 1;
-		mscr.bits.cfg_value = 0;
+		mscr = mii_read (dev, phy_addr, MII_MSCR);
+		mscr |= MII_MSCR_CFG_ENABLE;
+		mscr &= ~MII_MSCR_CFG_VALUE = 0;
 #endif
 #endif
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 		mdelay(10);
 		mdelay(10);
 	}
 	}
 	return 0;
 	return 0;
@@ -1627,43 +1631,42 @@ mii_set_media (struct net_device *dev)
 static int
 static int
 mii_get_media_pcs (struct net_device *dev)
 mii_get_media_pcs (struct net_device *dev)
 {
 {
-	ANAR_PCS_t negotiate;
-	BMSR_t bmsr;
-	BMCR_t bmcr;
+	__u16 negotiate;
+	__u16 bmsr;
 	int phy_addr;
 	int phy_addr;
 	struct netdev_private *np;
 	struct netdev_private *np;
 
 
 	np = netdev_priv(dev);
 	np = netdev_priv(dev);
 	phy_addr = np->phy_addr;
 	phy_addr = np->phy_addr;
 
 
-	bmsr.image = mii_read (dev, phy_addr, PCS_BMSR);
+	bmsr = mii_read (dev, phy_addr, PCS_BMSR);
 	if (np->an_enable) {
 	if (np->an_enable) {
-		if (!bmsr.bits.an_complete) {
+		if (!(bmsr & MII_BMSR_AN_COMPLETE)) {
 			/* Auto-Negotiation not completed */
 			/* Auto-Negotiation not completed */
 			return -1;
 			return -1;
 		}
 		}
-		negotiate.image = mii_read (dev, phy_addr, PCS_ANAR) &
+		negotiate = mii_read (dev, phy_addr, PCS_ANAR) &
 			mii_read (dev, phy_addr, PCS_ANLPAR);
 			mii_read (dev, phy_addr, PCS_ANLPAR);
 		np->speed = 1000;
 		np->speed = 1000;
-		if (negotiate.bits.full_duplex) {
+		if (negotiate & PCS_ANAR_FULL_DUPLEX) {
 			printk (KERN_INFO "Auto 1000 Mbps, Full duplex\n");
 			printk (KERN_INFO "Auto 1000 Mbps, Full duplex\n");
 			np->full_duplex = 1;
 			np->full_duplex = 1;
 		} else {
 		} else {
 			printk (KERN_INFO "Auto 1000 Mbps, half duplex\n");
 			printk (KERN_INFO "Auto 1000 Mbps, half duplex\n");
 			np->full_duplex = 0;
 			np->full_duplex = 0;
 		}
 		}
-		if (negotiate.bits.pause) {
+		if (negotiate & PCS_ANAR_PAUSE) {
 			np->tx_flow &= 1;
 			np->tx_flow &= 1;
 			np->rx_flow &= 1;
 			np->rx_flow &= 1;
-		} else if (negotiate.bits.asymmetric) {
+		} else if (negotiate & PCS_ANAR_ASYMMETRIC) {
 			np->tx_flow = 0;
 			np->tx_flow = 0;
 			np->rx_flow &= 1;
 			np->rx_flow &= 1;
 		}
 		}
 		/* else tx_flow, rx_flow = user select  */
 		/* else tx_flow, rx_flow = user select  */
 	} else {
 	} else {
-		bmcr.image = mii_read (dev, phy_addr, PCS_BMCR);
+		__u16 bmcr = mii_read (dev, phy_addr, PCS_BMCR);
 		printk (KERN_INFO "Operating at 1000 Mbps, ");
 		printk (KERN_INFO "Operating at 1000 Mbps, ");
-		if (bmcr.bits.duplex_mode) {
+		if (bmcr & MII_BMCR_DUPLEX_MODE) {
 			printk ("Full duplex\n");
 			printk ("Full duplex\n");
 		} else {
 		} else {
 			printk ("Half duplex\n");
 			printk ("Half duplex\n");
@@ -1684,9 +1687,9 @@ mii_get_media_pcs (struct net_device *dev)
 static int
 static int
 mii_set_media_pcs (struct net_device *dev)
 mii_set_media_pcs (struct net_device *dev)
 {
 {
-	BMCR_t bmcr;
-	ESR_t esr;
-	ANAR_PCS_t anar;
+	__u16 bmcr;
+	__u16 esr;
+	__u16 anar;
 	int phy_addr;
 	int phy_addr;
 	struct netdev_private *np;
 	struct netdev_private *np;
 	np = netdev_priv(dev);
 	np = netdev_priv(dev);
@@ -1695,41 +1698,37 @@ mii_set_media_pcs (struct net_device *dev)
 	/* Auto-Negotiation? */
 	/* Auto-Negotiation? */
 	if (np->an_enable) {
 	if (np->an_enable) {
 		/* Advertise capabilities */
 		/* Advertise capabilities */
-		esr.image = mii_read (dev, phy_addr, PCS_ESR);
-		anar.image = mii_read (dev, phy_addr, MII_ANAR);
-		anar.bits.half_duplex =
-			esr.bits.media_1000BT_HD | esr.bits.media_1000BX_HD;
-		anar.bits.full_duplex =
-			esr.bits.media_1000BT_FD | esr.bits.media_1000BX_FD;
-		anar.bits.pause = 1;
-		anar.bits.asymmetric = 1;
-		mii_write (dev, phy_addr, MII_ANAR, anar.image);
+		esr = mii_read (dev, phy_addr, PCS_ESR);
+		anar = mii_read (dev, phy_addr, MII_ANAR) &
+			~PCS_ANAR_HALF_DUPLEX &
+			~PCS_ANAR_FULL_DUPLEX;
+		if (esr & (MII_ESR_1000BT_HD | MII_ESR_1000BX_HD))
+			anar |= PCS_ANAR_HALF_DUPLEX;
+		if (esr & (MII_ESR_1000BT_FD | MII_ESR_1000BX_FD))
+			anar |= PCS_ANAR_FULL_DUPLEX;
+		anar |= PCS_ANAR_PAUSE | PCS_ANAR_ASYMMETRIC;
+		mii_write (dev, phy_addr, MII_ANAR, anar);
 
 
 		/* Soft reset PHY */
 		/* Soft reset PHY */
 		mii_write (dev, phy_addr, MII_BMCR, MII_BMCR_RESET);
 		mii_write (dev, phy_addr, MII_BMCR, MII_BMCR_RESET);
-		bmcr.image = 0;
-		bmcr.bits.an_enable = 1;
-		bmcr.bits.restart_an = 1;
-		bmcr.bits.reset = 1;
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		bmcr = MII_BMCR_AN_ENABLE | MII_BMCR_RESTART_AN |
+		       MII_BMCR_RESET;
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 		mdelay(1);
 		mdelay(1);
 	} else {
 	} else {
 		/* Force speed setting */
 		/* Force speed setting */
 		/* PHY Reset */
 		/* PHY Reset */
-		bmcr.image = 0;
-		bmcr.bits.reset = 1;
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		bmcr = MII_BMCR_RESET;
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 		mdelay(10);
 		mdelay(10);
-		bmcr.image = 0;
-		bmcr.bits.an_enable = 0;
 		if (np->full_duplex) {
 		if (np->full_duplex) {
-			bmcr.bits.duplex_mode = 1;
+			bmcr = MII_BMCR_DUPLEX_MODE;
 			printk (KERN_INFO "Manual full duplex\n");
 			printk (KERN_INFO "Manual full duplex\n");
 		} else {
 		} else {
-			bmcr.bits.duplex_mode = 0;
+			bmcr = 0;
 			printk (KERN_INFO "Manual half duplex\n");
 			printk (KERN_INFO "Manual half duplex\n");
 		}
 		}
-		mii_write (dev, phy_addr, MII_BMCR, bmcr.image);
+		mii_write (dev, phy_addr, MII_BMCR, bmcr);
 		mdelay(10);
 		mdelay(10);
 
 
 		/*  Advertise nothing */
 		/*  Advertise nothing */

+ 2 - 155
drivers/net/dl2k.h

@@ -298,23 +298,6 @@ enum _pcs_reg {
 };
 };
 
 
 /* Basic Mode Control Register */
 /* Basic Mode Control Register */
-typedef union t_MII_BMCR {
-	u16 image;
-	struct {
-		u16 _bit_5_0:6;	// bit 5:0
-		u16 speed1000:1;	// bit 6
-		u16 col_test_enable:1;	// bit 7
-		u16 duplex_mode:1;	// bit 8
-		u16 restart_an:1;	// bit 9
-		u16 isolate:1;	// bit 10
-		u16 power_down:1;	// bit 11
-		u16 an_enable:1;	// bit 12
-		u16 speed100:1;	// bit 13
-		u16 loopback:1;	// bit 14
-		u16 reset:1;	// bit 15
-	} bits;
-} BMCR_t, *PBMCR_t;
-
 enum _mii_bmcr {
 enum _mii_bmcr {
 	MII_BMCR_RESET = 0x8000,
 	MII_BMCR_RESET = 0x8000,
 	MII_BMCR_LOOP_BACK = 0x4000,
 	MII_BMCR_LOOP_BACK = 0x4000,
@@ -333,28 +316,6 @@ enum _mii_bmcr {
 };
 };
 
 
 /* Basic Mode Status Register */
 /* Basic Mode Status Register */
-typedef union t_MII_BMSR {
-	u16 image;
-	struct {
-		u16 ext_capability:1;	// bit 0
-		u16 japper_detect:1;	// bit 1
-		u16 link_status:1;	// bit 2
-		u16 an_ability:1;	// bit 3
-		u16 remote_fault:1;	// bit 4
-		u16 an_complete:1;	// bit 5
-		u16 preamble_supp:1;	// bit 6
-		u16 _bit_7:1;	// bit 7
-		u16 ext_status:1;	// bit 8
-		u16 media_100BT2_HD:1;	// bit 9
-		u16 media_100BT2_FD:1;	// bit 10
-		u16 media_10BT_HD:1;	// bit 11
-		u16 media_10BT_FD:1;	// bit 12
-		u16 media_100BX_HD:1;	// bit 13
-		u16 media_100BX_FD:1;	// bit 14
-		u16 media_100BT4:1;	// bit 15
-	} bits;
-} BMSR_t, *PBMSR_t;
-
 enum _mii_bmsr {
 enum _mii_bmsr {
 	MII_BMSR_100BT4 = 0x8000,
 	MII_BMSR_100BT4 = 0x8000,
 	MII_BMSR_100BX_FD = 0x4000,
 	MII_BMSR_100BX_FD = 0x4000,
@@ -374,24 +335,6 @@ enum _mii_bmsr {
 };
 };
 
 
 /* ANAR */
 /* ANAR */
-typedef union t_MII_ANAR {
-	u16 image;
-	struct {
-		u16 selector:5;	// bit 4:0
-		u16 media_10BT_HD:1;	// bit 5
-		u16 media_10BT_FD:1;	// bit 6
-		u16 media_100BX_HD:1;	// bit 7
-		u16 media_100BX_FD:1;	// bit 8
-		u16 media_100BT4:1;	// bit 9
-		u16 pause:1;	// bit 10
-		u16 asymmetric:1;	// bit 11
-		u16 _bit12:1;	// bit 12
-		u16 remote_fault:1;	// bit 13
-		u16 _bit14:1;	// bit 14
-		u16 next_page:1;	// bit 15
-	} bits;
-} ANAR_t, *PANAR_t;
-
 enum _mii_anar {
 enum _mii_anar {
 	MII_ANAR_NEXT_PAGE = 0x8000,
 	MII_ANAR_NEXT_PAGE = 0x8000,
 	MII_ANAR_REMOTE_FAULT = 0x4000,
 	MII_ANAR_REMOTE_FAULT = 0x4000,
@@ -407,24 +350,6 @@ enum _mii_anar {
 };
 };
 
 
 /* ANLPAR */
 /* ANLPAR */
-typedef union t_MII_ANLPAR {
-	u16 image;
-	struct {
-		u16 selector:5;	// bit 4:0
-		u16 media_10BT_HD:1;	// bit 5
-		u16 media_10BT_FD:1;	// bit 6
-		u16 media_100BX_HD:1;	// bit 7
-		u16 media_100BX_FD:1;	// bit 8
-		u16 media_100BT4:1;	// bit 9
-		u16 pause:1;	// bit 10
-		u16 asymmetric:1;	// bit 11
-		u16 _bit12:1;	// bit 12
-		u16 remote_fault:1;	// bit 13
-		u16 _bit14:1;	// bit 14
-		u16 next_page:1;	// bit 15
-	} bits;
-} ANLPAR_t, *PANLPAR_t;
-
 enum _mii_anlpar {
 enum _mii_anlpar {
 	MII_ANLPAR_NEXT_PAGE = MII_ANAR_NEXT_PAGE,
 	MII_ANLPAR_NEXT_PAGE = MII_ANAR_NEXT_PAGE,
 	MII_ANLPAR_REMOTE_FAULT = MII_ANAR_REMOTE_FAULT,
 	MII_ANLPAR_REMOTE_FAULT = MII_ANAR_REMOTE_FAULT,
@@ -439,18 +364,6 @@ enum _mii_anlpar {
 };
 };
 
 
 /* Auto-Negotiation Expansion Register */
 /* Auto-Negotiation Expansion Register */
-typedef union t_MII_ANER {
-	u16 image;
-	struct {
-		u16 lp_negotiable:1;	// bit 0
-		u16 page_received:1;	// bit 1
-		u16 nextpagable:1;	// bit 2
-		u16 lp_nextpagable:1;	// bit 3
-		u16 pdetect_fault:1;	// bit 4
-		u16 _bit15_5:11;	// bit 15:5
-	} bits;
-} ANER_t, *PANER_t;
-
 enum _mii_aner {
 enum _mii_aner {
 	MII_ANER_PAR_DETECT_FAULT = 0x0010,
 	MII_ANER_PAR_DETECT_FAULT = 0x0010,
 	MII_ANER_LP_NEXTPAGABLE = 0x0008,
 	MII_ANER_LP_NEXTPAGABLE = 0x0008,
@@ -460,19 +373,6 @@ enum _mii_aner {
 };
 };
 
 
 /* MASTER-SLAVE Control Register */
 /* MASTER-SLAVE Control Register */
-typedef union t_MII_MSCR {
-	u16 image;
-	struct {
-		u16 _bit_7_0:8;	// bit 7:0
-		u16 media_1000BT_HD:1;	// bit 8
-		u16 media_1000BT_FD:1;	// bit 9
-		u16 port_type:1;	// bit 10
-		u16 cfg_value:1;	// bit 11
-		u16 cfg_enable:1;	// bit 12
-		u16 test_mode:3;	// bit 15:13
-	} bits;
-} MSCR_t, *PMSCR_t;
-
 enum _mii_mscr {
 enum _mii_mscr {
 	MII_MSCR_TEST_MODE = 0xe000,
 	MII_MSCR_TEST_MODE = 0xe000,
 	MII_MSCR_CFG_ENABLE = 0x1000,
 	MII_MSCR_CFG_ENABLE = 0x1000,
@@ -483,20 +383,6 @@ enum _mii_mscr {
 };
 };
 
 
 /* MASTER-SLAVE Status Register */
 /* MASTER-SLAVE Status Register */
-typedef union t_MII_MSSR {
-	u16 image;
-	struct {
-		u16 idle_err_count:8;	// bit 7:0
-		u16 _bit_9_8:2;	// bit 9:8
-		u16 lp_1000BT_HD:1;	// bit 10
-		u16 lp_1000BT_FD:1;	// bit 11
-		u16 remote_rcv_status:1;	// bit 12
-		u16 local_rcv_status:1;	// bit 13
-		u16 cfg_resolution:1;	// bit 14
-		u16 cfg_fault:1;	// bit 15
-	} bits;
-} MSSR_t, *PMSSR_t;
-
 enum _mii_mssr {
 enum _mii_mssr {
 	MII_MSSR_CFG_FAULT = 0x8000,
 	MII_MSSR_CFG_FAULT = 0x8000,
 	MII_MSSR_CFG_RES = 0x4000,
 	MII_MSSR_CFG_RES = 0x4000,
@@ -508,17 +394,6 @@ enum _mii_mssr {
 };
 };
 
 
 /* IEEE Extened Status Register */
 /* IEEE Extened Status Register */
-typedef union t_MII_ESR {
-	u16 image;
-	struct {
-		u16 _bit_11_0:12;	// bit 11:0
-		u16 media_1000BT_HD:2;	// bit 12
-		u16 media_1000BT_FD:1;	// bit 13
-		u16 media_1000BX_HD:1;	// bit 14
-		u16 media_1000BX_FD:1;	// bit 15
-	} bits;
-} ESR_t, *PESR_t;
-
 enum _mii_esr {
 enum _mii_esr {
 	MII_ESR_1000BX_FD = 0x8000,
 	MII_ESR_1000BX_FD = 0x8000,
 	MII_ESR_1000BX_HD = 0x4000,
 	MII_ESR_1000BX_HD = 0x4000,
@@ -526,6 +401,7 @@ enum _mii_esr {
 	MII_ESR_1000BT_HD = 0x1000,
 	MII_ESR_1000BT_HD = 0x1000,
 };
 };
 /* PHY Specific Control Register */
 /* PHY Specific Control Register */
+#if 0
 typedef union t_MII_PHY_SCR {
 typedef union t_MII_PHY_SCR {
 	u16 image;
 	u16 image;
 	struct {
 	struct {
@@ -543,6 +419,7 @@ typedef union t_MII_PHY_SCR {
 		u16 xmit_fifo_depth:2;	// bit 15:14
 		u16 xmit_fifo_depth:2;	// bit 15:14
 	} bits;
 	} bits;
 } PHY_SCR_t, *PPHY_SCR_t;
 } PHY_SCR_t, *PPHY_SCR_t;
+#endif
 
 
 typedef enum t_MII_ADMIN_STATUS {
 typedef enum t_MII_ADMIN_STATUS {
 	adm_reset,
 	adm_reset,
@@ -556,21 +433,6 @@ typedef enum t_MII_ADMIN_STATUS {
 /* PCS control and status registers bitmap as the same as MII */
 /* PCS control and status registers bitmap as the same as MII */
 /* PCS Extended Status register bitmap as the same as MII */
 /* PCS Extended Status register bitmap as the same as MII */
 /* PCS ANAR */
 /* PCS ANAR */
-typedef union t_PCS_ANAR {
-	u16 image;
-	struct {
-		u16 _bit_4_0:5;		// bit 4:0
-		u16 full_duplex:1;	// bit 5
-		u16 half_duplex:1;	// bit 6
-		u16 asymmetric:1;	// bit 7
-		u16 pause:1;		// bit 8
-		u16 _bit_11_9:3;	// bit 11:9
-		u16 remote_fault:2;	// bit 13:12
-		u16 _bit_14:1;		// bit 14
-		u16 next_page:1;	// bit 15
-	} bits;
-} ANAR_PCS_t, *PANAR_PCS_t;
-
 enum _pcs_anar {
 enum _pcs_anar {
 	PCS_ANAR_NEXT_PAGE = 0x8000,
 	PCS_ANAR_NEXT_PAGE = 0x8000,
 	PCS_ANAR_REMOTE_FAULT = 0x3000,
 	PCS_ANAR_REMOTE_FAULT = 0x3000,
@@ -580,21 +442,6 @@ enum _pcs_anar {
 	PCS_ANAR_FULL_DUPLEX = 0x0020,
 	PCS_ANAR_FULL_DUPLEX = 0x0020,
 };
 };
 /* PCS ANLPAR */
 /* PCS ANLPAR */
-typedef union t_PCS_ANLPAR {
-	u16 image;
-	struct {
-		u16 _bit_4_0:5;		// bit 4:0
-		u16 full_duplex:1;	// bit 5
-		u16 half_duplex:1;	// bit 6
-		u16 asymmetric:1;	// bit 7
-		u16 pause:1;		// bit 8
-		u16 _bit_11_9:3;	// bit 11:9
-		u16 remote_fault:2;	// bit 13:12
-		u16 _bit_14:1;		// bit 14
-		u16 next_page:1;	// bit 15
-	} bits;
-} ANLPAR_PCS_t, *PANLPAR_PCS_t;
-
 enum _pcs_anlpar {
 enum _pcs_anlpar {
 	PCS_ANLPAR_NEXT_PAGE = PCS_ANAR_NEXT_PAGE,
 	PCS_ANLPAR_NEXT_PAGE = PCS_ANAR_NEXT_PAGE,
 	PCS_ANLPAR_REMOTE_FAULT = PCS_ANAR_REMOTE_FAULT,
 	PCS_ANLPAR_REMOTE_FAULT = PCS_ANAR_REMOTE_FAULT,

+ 12 - 24
drivers/net/ipg.c

@@ -857,21 +857,14 @@ static void init_tfdlist(struct net_device *dev)
 static void ipg_nic_txfree(struct net_device *dev)
 static void ipg_nic_txfree(struct net_device *dev)
 {
 {
 	struct ipg_nic_private *sp = netdev_priv(dev);
 	struct ipg_nic_private *sp = netdev_priv(dev);
-	void __iomem *ioaddr = sp->ioaddr;
-	unsigned int curr;
-	u64 txd_map;
-	unsigned int released, pending;
-
-	txd_map = (u64)sp->txd_map;
-	curr = ipg_r32(TFD_LIST_PTR_0) -
-		do_div(txd_map, sizeof(struct ipg_tx)) - 1;
+	unsigned int released, pending, dirty;
 
 
 	IPG_DEBUG_MSG("_nic_txfree\n");
 	IPG_DEBUG_MSG("_nic_txfree\n");
 
 
 	pending = sp->tx_current - sp->tx_dirty;
 	pending = sp->tx_current - sp->tx_dirty;
+	dirty = sp->tx_dirty % IPG_TFDLIST_LENGTH;
 
 
 	for (released = 0; released < pending; released++) {
 	for (released = 0; released < pending; released++) {
-		unsigned int dirty = sp->tx_dirty % IPG_TFDLIST_LENGTH;
 		struct sk_buff *skb = sp->TxBuff[dirty];
 		struct sk_buff *skb = sp->TxBuff[dirty];
 		struct ipg_tx *txfd = sp->txd + dirty;
 		struct ipg_tx *txfd = sp->txd + dirty;
 
 
@@ -882,11 +875,8 @@ static void ipg_nic_txfree(struct net_device *dev)
 		 * If the TFDDone bit is set, free the associated
 		 * If the TFDDone bit is set, free the associated
 		 * buffer.
 		 * buffer.
 		 */
 		 */
-		if (dirty == curr)
-			break;
-
-		/* Setup TFDDONE for compatible issue. */
-		txfd->tfc |= cpu_to_le64(IPG_TFC_TFDDONE);
+		if (!(txfd->tfc & cpu_to_le64(IPG_TFC_TFDDONE)))
+                        break;
 
 
 		/* Free the transmit buffer. */
 		/* Free the transmit buffer. */
 		if (skb) {
 		if (skb) {
@@ -898,6 +888,7 @@ static void ipg_nic_txfree(struct net_device *dev)
 
 
 			sp->TxBuff[dirty] = NULL;
 			sp->TxBuff[dirty] = NULL;
 		}
 		}
+		dirty = (dirty + 1) % IPG_TFDLIST_LENGTH;
 	}
 	}
 
 
 	sp->tx_dirty += released;
 	sp->tx_dirty += released;
@@ -1630,6 +1621,8 @@ static irqreturn_t ipg_interrupt_handler(int irq, void *dev_inst)
 #ifdef JUMBO_FRAME
 #ifdef JUMBO_FRAME
 	ipg_nic_rxrestore(dev);
 	ipg_nic_rxrestore(dev);
 #endif
 #endif
+	spin_lock(&sp->lock);
+
 	/* Get interrupt source information, and acknowledge
 	/* Get interrupt source information, and acknowledge
 	 * some (i.e. TxDMAComplete, RxDMAComplete, RxEarly,
 	 * some (i.e. TxDMAComplete, RxDMAComplete, RxEarly,
 	 * IntRequested, MacControlFrame, LinkEvent) interrupts
 	 * IntRequested, MacControlFrame, LinkEvent) interrupts
@@ -1647,9 +1640,7 @@ static irqreturn_t ipg_interrupt_handler(int irq, void *dev_inst)
 	handled = 1;
 	handled = 1;
 
 
 	if (unlikely(!netif_running(dev)))
 	if (unlikely(!netif_running(dev)))
-		goto out;
-
-	spin_lock(&sp->lock);
+		goto out_unlock;
 
 
 	/* If RFDListEnd interrupt, restore all used RFDs. */
 	/* If RFDListEnd interrupt, restore all used RFDs. */
 	if (status & IPG_IS_RFD_LIST_END) {
 	if (status & IPG_IS_RFD_LIST_END) {
@@ -1733,9 +1724,9 @@ out_enable:
 	ipg_w16(IPG_IE_TX_DMA_COMPLETE | IPG_IE_RX_DMA_COMPLETE |
 	ipg_w16(IPG_IE_TX_DMA_COMPLETE | IPG_IE_RX_DMA_COMPLETE |
 		IPG_IE_HOST_ERROR | IPG_IE_INT_REQUESTED | IPG_IE_TX_COMPLETE |
 		IPG_IE_HOST_ERROR | IPG_IE_INT_REQUESTED | IPG_IE_TX_COMPLETE |
 		IPG_IE_LINK_EVENT | IPG_IE_UPDATE_STATS, INT_ENABLE);
 		IPG_IE_LINK_EVENT | IPG_IE_UPDATE_STATS, INT_ENABLE);
-
+out_unlock:
 	spin_unlock(&sp->lock);
 	spin_unlock(&sp->lock);
-out:
+
 	return IRQ_RETVAL(handled);
 	return IRQ_RETVAL(handled);
 }
 }
 
 
@@ -1943,10 +1934,7 @@ static int ipg_nic_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
 	 */
 	 */
 	if (sp->tenmbpsmode)
 	if (sp->tenmbpsmode)
 		txfd->tfc |= cpu_to_le64(IPG_TFC_TXINDICATE);
 		txfd->tfc |= cpu_to_le64(IPG_TFC_TXINDICATE);
-	else if (!((sp->tx_current - sp->tx_dirty + 1) >
-	    IPG_FRAMESBETWEENTXDMACOMPLETES)) {
-		txfd->tfc |= cpu_to_le64(IPG_TFC_TXDMAINDICATE);
-	}
+	txfd->tfc |= cpu_to_le64(IPG_TFC_TXDMAINDICATE);
 	/* Based on compilation option, determine if FCS is to be
 	/* Based on compilation option, determine if FCS is to be
 	 * appended to transmit frame by IPG.
 	 * appended to transmit frame by IPG.
 	 */
 	 */
@@ -2003,7 +1991,7 @@ static int ipg_nic_hard_start_xmit(struct sk_buff *skb, struct net_device *dev)
 	ipg_w32(IPG_DC_TX_DMA_POLL_NOW, DMA_CTRL);
 	ipg_w32(IPG_DC_TX_DMA_POLL_NOW, DMA_CTRL);
 
 
 	if (sp->tx_current == (sp->tx_dirty + IPG_TFDLIST_LENGTH))
 	if (sp->tx_current == (sp->tx_dirty + IPG_TFDLIST_LENGTH))
-		netif_wake_queue(dev);
+		netif_stop_queue(dev);
 
 
 	spin_unlock_irqrestore(&sp->lock, flags);
 	spin_unlock_irqrestore(&sp->lock, flags);
 
 

+ 17 - 14
drivers/net/pcmcia/3c574_cs.c

@@ -187,14 +187,16 @@ enum Window1 {
 enum Window3 {			/* Window 3: MAC/config bits. */
 enum Window3 {			/* Window 3: MAC/config bits. */
 	Wn3_Config=0, Wn3_MAC_Ctrl=6, Wn3_Options=8,
 	Wn3_Config=0, Wn3_MAC_Ctrl=6, Wn3_Options=8,
 };
 };
-union wn3_config {
-	int i;
-	struct w3_config_fields {
-		unsigned int ram_size:3, ram_width:1, ram_speed:2, rom_size:2;
-		int pad8:8;
-		unsigned int ram_split:2, pad18:2, xcvr:3, pad21:1, autoselect:1;
-		int pad24:7;
-	} u;
+enum wn3_config {
+	Ram_size = 7,
+	Ram_width = 8,
+	Ram_speed = 0x30,
+	Rom_size = 0xc0,
+	Ram_split_shift = 16,
+	Ram_split = 3 << Ram_split_shift,
+	Xcvr_shift = 20,
+	Xcvr = 7 << Xcvr_shift,
+	Autoselect = 0x1000000,
 };
 };
 
 
 enum Window4 {		/* Window 4: Xcvr/media bits. */
 enum Window4 {		/* Window 4: Xcvr/media bits. */
@@ -342,7 +344,7 @@ static int tc574_config(struct pcmcia_device *link)
 	kio_addr_t ioaddr;
 	kio_addr_t ioaddr;
 	__be16 *phys_addr;
 	__be16 *phys_addr;
 	char *cardname;
 	char *cardname;
-	union wn3_config config;
+	__u32 config;
 	DECLARE_MAC_BUF(mac);
 	DECLARE_MAC_BUF(mac);
 
 
 	phys_addr = (__be16 *)dev->dev_addr;
 	phys_addr = (__be16 *)dev->dev_addr;
@@ -401,9 +403,9 @@ static int tc574_config(struct pcmcia_device *link)
 		outw(0<<11, ioaddr + RunnerRdCtrl);
 		outw(0<<11, ioaddr + RunnerRdCtrl);
 		printk(KERN_INFO "  ASIC rev %d,", mcr>>3);
 		printk(KERN_INFO "  ASIC rev %d,", mcr>>3);
 		EL3WINDOW(3);
 		EL3WINDOW(3);
-		config.i = inl(ioaddr + Wn3_Config);
-		lp->default_media = config.u.xcvr;
-		lp->autoselect = config.u.autoselect;
+		config = inl(ioaddr + Wn3_Config);
+		lp->default_media = (config & Xcvr) >> Xcvr_shift;
+		lp->autoselect = config & Autoselect ? 1 : 0;
 	}
 	}
 
 
 	init_timer(&lp->media);
 	init_timer(&lp->media);
@@ -464,8 +466,9 @@ static int tc574_config(struct pcmcia_device *link)
 	       dev->name, cardname, dev->base_addr, dev->irq,
 	       dev->name, cardname, dev->base_addr, dev->irq,
 	       print_mac(mac, dev->dev_addr));
 	       print_mac(mac, dev->dev_addr));
 	printk(" %dK FIFO split %s Rx:Tx, %sMII interface.\n",
 	printk(" %dK FIFO split %s Rx:Tx, %sMII interface.\n",
-		   8 << config.u.ram_size, ram_split[config.u.ram_split],
-		   config.u.autoselect ? "autoselect " : "");
+		   8 << config & Ram_size,
+		   ram_split[(config & Ram_split) >> Ram_split_shift],
+		   config & Autoselect ? "autoselect " : "");
 
 
 	return 0;
 	return 0;
 
 

+ 12 - 5
drivers/net/s2io.c

@@ -84,7 +84,7 @@
 #include "s2io.h"
 #include "s2io.h"
 #include "s2io-regs.h"
 #include "s2io-regs.h"
 
 
-#define DRV_VERSION "2.0.26.10"
+#define DRV_VERSION "2.0.26.17"
 
 
 /* S2io Driver name & version. */
 /* S2io Driver name & version. */
 static char s2io_driver_name[] = "Neterion";
 static char s2io_driver_name[] = "Neterion";
@@ -3848,8 +3848,6 @@ static int s2io_open(struct net_device *dev)
 	netif_carrier_off(dev);
 	netif_carrier_off(dev);
 	sp->last_link_state = 0;
 	sp->last_link_state = 0;
 
 
-	napi_enable(&sp->napi);
-
 	if (sp->config.intr_type == MSI_X) {
 	if (sp->config.intr_type == MSI_X) {
 		int ret = s2io_enable_msi_x(sp);
 		int ret = s2io_enable_msi_x(sp);
 
 
@@ -3892,7 +3890,6 @@ static int s2io_open(struct net_device *dev)
 	return 0;
 	return 0;
 
 
 hw_init_failed:
 hw_init_failed:
-	napi_disable(&sp->napi);
 	if (sp->config.intr_type == MSI_X) {
 	if (sp->config.intr_type == MSI_X) {
 		if (sp->entries) {
 		if (sp->entries) {
 			kfree(sp->entries);
 			kfree(sp->entries);
@@ -3932,7 +3929,6 @@ static int s2io_close(struct net_device *dev)
 		return 0;
 		return 0;
 
 
 	netif_stop_queue(dev);
 	netif_stop_queue(dev);
-	napi_disable(&sp->napi);
 	/* Reset card, kill tasklet and free Tx and Rx buffers. */
 	/* Reset card, kill tasklet and free Tx and Rx buffers. */
 	s2io_card_down(sp);
 	s2io_card_down(sp);
 
 
@@ -6796,6 +6792,8 @@ static void do_s2io_card_down(struct s2io_nic * sp, int do_io)
 	struct XENA_dev_config __iomem *bar0 = sp->bar0;
 	struct XENA_dev_config __iomem *bar0 = sp->bar0;
 	unsigned long flags;
 	unsigned long flags;
 	register u64 val64 = 0;
 	register u64 val64 = 0;
+	struct config_param *config;
+	config = &sp->config;
 
 
 	if (!is_s2io_card_up(sp))
 	if (!is_s2io_card_up(sp))
 		return;
 		return;
@@ -6807,6 +6805,10 @@ static void do_s2io_card_down(struct s2io_nic * sp, int do_io)
 	}
 	}
 	clear_bit(__S2IO_STATE_CARD_UP, &sp->state);
 	clear_bit(__S2IO_STATE_CARD_UP, &sp->state);
 
 
+	/* Disable napi */
+	if (config->napi)
+		napi_disable(&sp->napi);
+
 	/* disable Tx and Rx traffic on the NIC */
 	/* disable Tx and Rx traffic on the NIC */
 	if (do_io)
 	if (do_io)
 		stop_nic(sp);
 		stop_nic(sp);
@@ -6900,6 +6902,11 @@ static int s2io_card_up(struct s2io_nic * sp)
 		DBG_PRINT(INFO_DBG, "Buf in ring:%d is %d:\n", i,
 		DBG_PRINT(INFO_DBG, "Buf in ring:%d is %d:\n", i,
 			  atomic_read(&sp->rx_bufs_left[i]));
 			  atomic_read(&sp->rx_bufs_left[i]));
 	}
 	}
+
+	/* Initialise napi */
+	if (config->napi)
+		napi_enable(&sp->napi);
+
 	/* Maintain the state prior to the open */
 	/* Maintain the state prior to the open */
 	if (sp->promisc_flg)
 	if (sp->promisc_flg)
 		sp->promisc_flg = 0;
 		sp->promisc_flg = 0;

+ 19 - 5
drivers/net/sky2.c

@@ -3949,7 +3949,7 @@ static __exit void sky2_debug_cleanup(void)
 /* Initialize network device */
 /* Initialize network device */
 static __devinit struct net_device *sky2_init_netdev(struct sky2_hw *hw,
 static __devinit struct net_device *sky2_init_netdev(struct sky2_hw *hw,
 						     unsigned port,
 						     unsigned port,
-						     int highmem)
+						     int highmem, int wol)
 {
 {
 	struct sky2_port *sky2;
 	struct sky2_port *sky2;
 	struct net_device *dev = alloc_etherdev(sizeof(*sky2));
 	struct net_device *dev = alloc_etherdev(sizeof(*sky2));
@@ -3989,7 +3989,7 @@ static __devinit struct net_device *sky2_init_netdev(struct sky2_hw *hw,
 	sky2->speed = -1;
 	sky2->speed = -1;
 	sky2->advertising = sky2_supported_modes(hw);
 	sky2->advertising = sky2_supported_modes(hw);
 	sky2->rx_csum = (hw->chip_id != CHIP_ID_YUKON_XL);
 	sky2->rx_csum = (hw->chip_id != CHIP_ID_YUKON_XL);
-	sky2->wol = sky2_wol_supported(hw) & WAKE_MAGIC;
+	sky2->wol = wol;
 
 
 	spin_lock_init(&sky2->phy_lock);
 	spin_lock_init(&sky2->phy_lock);
 	sky2->tx_pending = TX_DEF_PENDING;
 	sky2->tx_pending = TX_DEF_PENDING;
@@ -4086,12 +4086,24 @@ static int __devinit sky2_test_msi(struct sky2_hw *hw)
 	return err;
 	return err;
 }
 }
 
 
+static int __devinit pci_wake_enabled(struct pci_dev *dev)
+{
+	int pm  = pci_find_capability(dev, PCI_CAP_ID_PM);
+	u16 value;
+
+	if (!pm)
+		return 0;
+	if (pci_read_config_word(dev, pm + PCI_PM_CTRL, &value))
+		return 0;
+	return value & PCI_PM_CTRL_PME_ENABLE;
+}
+
 static int __devinit sky2_probe(struct pci_dev *pdev,
 static int __devinit sky2_probe(struct pci_dev *pdev,
 				const struct pci_device_id *ent)
 				const struct pci_device_id *ent)
 {
 {
 	struct net_device *dev;
 	struct net_device *dev;
 	struct sky2_hw *hw;
 	struct sky2_hw *hw;
-	int err, using_dac = 0;
+	int err, using_dac = 0, wol_default;
 
 
 	err = pci_enable_device(pdev);
 	err = pci_enable_device(pdev);
 	if (err) {
 	if (err) {
@@ -4124,6 +4136,8 @@ static int __devinit sky2_probe(struct pci_dev *pdev,
 		}
 		}
 	}
 	}
 
 
+	wol_default = pci_wake_enabled(pdev) ? WAKE_MAGIC : 0;
+
 	err = -ENOMEM;
 	err = -ENOMEM;
 	hw = kzalloc(sizeof(*hw), GFP_KERNEL);
 	hw = kzalloc(sizeof(*hw), GFP_KERNEL);
 	if (!hw) {
 	if (!hw) {
@@ -4167,7 +4181,7 @@ static int __devinit sky2_probe(struct pci_dev *pdev,
 
 
 	sky2_reset(hw);
 	sky2_reset(hw);
 
 
-	dev = sky2_init_netdev(hw, 0, using_dac);
+	dev = sky2_init_netdev(hw, 0, using_dac, wol_default);
 	if (!dev) {
 	if (!dev) {
 		err = -ENOMEM;
 		err = -ENOMEM;
 		goto err_out_free_pci;
 		goto err_out_free_pci;
@@ -4204,7 +4218,7 @@ static int __devinit sky2_probe(struct pci_dev *pdev,
 	if (hw->ports > 1) {
 	if (hw->ports > 1) {
 		struct net_device *dev1;
 		struct net_device *dev1;
 
 
-		dev1 = sky2_init_netdev(hw, 1, using_dac);
+		dev1 = sky2_init_netdev(hw, 1, using_dac, wol_default);
 		if (!dev1)
 		if (!dev1)
 			dev_warn(&pdev->dev, "allocation for second device failed\n");
 			dev_warn(&pdev->dev, "allocation for second device failed\n");
 		else if ((err = register_netdev(dev1))) {
 		else if ((err = register_netdev(dev1))) {

+ 49 - 45
drivers/net/wan/dscc4.c

@@ -139,19 +139,21 @@ struct thingie {
 };
 };
 
 
 struct TxFD {
 struct TxFD {
-	u32 state;
-	u32 next;
-	u32 data;
-	u32 complete;
+	__le32 state;
+	__le32 next;
+	__le32 data;
+	__le32 complete;
 	u32 jiffies; /* Allows sizeof(TxFD) == sizeof(RxFD) + extra hack */
 	u32 jiffies; /* Allows sizeof(TxFD) == sizeof(RxFD) + extra hack */
+		     /* FWIW, datasheet calls that "dummy" and says that card
+		      * never looks at it; neither does the driver */
 };
 };
 
 
 struct RxFD {
 struct RxFD {
-	u32 state1;
-	u32 next;
-	u32 data;
-	u32 state2;
-	u32 end;
+	__le32 state1;
+	__le32 next;
+	__le32 data;
+	__le32 state2;
+	__le32 end;
 };
 };
 
 
 #define DUMMY_SKB_SIZE		64
 #define DUMMY_SKB_SIZE		64
@@ -181,7 +183,7 @@ struct RxFD {
 #define SCC_REG_START(dpriv)	(SCC_START+(dpriv->dev_id)*SCC_OFFSET)
 #define SCC_REG_START(dpriv)	(SCC_START+(dpriv->dev_id)*SCC_OFFSET)
 
 
 struct dscc4_pci_priv {
 struct dscc4_pci_priv {
-        u32 *iqcfg;
+        __le32 *iqcfg;
         int cfg_cur;
         int cfg_cur;
         spinlock_t lock;
         spinlock_t lock;
         struct pci_dev *pdev;
         struct pci_dev *pdev;
@@ -197,8 +199,8 @@ struct dscc4_dev_priv {
 
 
         struct RxFD *rx_fd;
         struct RxFD *rx_fd;
         struct TxFD *tx_fd;
         struct TxFD *tx_fd;
-        u32 *iqrx;
-        u32 *iqtx;
+        __le32 *iqrx;
+        __le32 *iqtx;
 
 
 	/* FIXME: check all the volatile are required */
 	/* FIXME: check all the volatile are required */
         volatile u32 tx_current;
         volatile u32 tx_current;
@@ -298,7 +300,7 @@ struct dscc4_dev_priv {
 #define BrrExpMask	0x00000f00
 #define BrrExpMask	0x00000f00
 #define BrrMultMask	0x0000003f
 #define BrrMultMask	0x0000003f
 #define EncodingMask	0x00700000
 #define EncodingMask	0x00700000
-#define Hold		0x40000000
+#define Hold		cpu_to_le32(0x40000000)
 #define SccBusy		0x10000000
 #define SccBusy		0x10000000
 #define PowerUp		0x80000000
 #define PowerUp		0x80000000
 #define Vis		0x00001000
 #define Vis		0x00001000
@@ -307,14 +309,14 @@ struct dscc4_dev_priv {
 #define FrameRdo	0x40
 #define FrameRdo	0x40
 #define FrameCrc	0x20
 #define FrameCrc	0x20
 #define FrameRab	0x10
 #define FrameRab	0x10
-#define FrameAborted	0x00000200
-#define FrameEnd	0x80000000
-#define DataComplete	0x40000000
+#define FrameAborted	cpu_to_le32(0x00000200)
+#define FrameEnd	cpu_to_le32(0x80000000)
+#define DataComplete	cpu_to_le32(0x40000000)
 #define LengthCheck	0x00008000
 #define LengthCheck	0x00008000
 #define SccEvt		0x02000000
 #define SccEvt		0x02000000
 #define NoAck		0x00000200
 #define NoAck		0x00000200
 #define Action		0x00000001
 #define Action		0x00000001
-#define HiDesc		0x20000000
+#define HiDesc		cpu_to_le32(0x20000000)
 
 
 /* SCC events */
 /* SCC events */
 #define RxEvt		0xf0000000
 #define RxEvt		0xf0000000
@@ -489,8 +491,8 @@ static void dscc4_release_ring(struct dscc4_dev_priv *dpriv)
 	skbuff = dpriv->tx_skbuff;
 	skbuff = dpriv->tx_skbuff;
 	for (i = 0; i < TX_RING_SIZE; i++) {
 	for (i = 0; i < TX_RING_SIZE; i++) {
 		if (*skbuff) {
 		if (*skbuff) {
-			pci_unmap_single(pdev, tx_fd->data, (*skbuff)->len,
-				PCI_DMA_TODEVICE);
+			pci_unmap_single(pdev, le32_to_cpu(tx_fd->data),
+				(*skbuff)->len, PCI_DMA_TODEVICE);
 			dev_kfree_skb(*skbuff);
 			dev_kfree_skb(*skbuff);
 		}
 		}
 		skbuff++;
 		skbuff++;
@@ -500,7 +502,7 @@ static void dscc4_release_ring(struct dscc4_dev_priv *dpriv)
 	skbuff = dpriv->rx_skbuff;
 	skbuff = dpriv->rx_skbuff;
 	for (i = 0; i < RX_RING_SIZE; i++) {
 	for (i = 0; i < RX_RING_SIZE; i++) {
 		if (*skbuff) {
 		if (*skbuff) {
-			pci_unmap_single(pdev, rx_fd->data,
+			pci_unmap_single(pdev, le32_to_cpu(rx_fd->data),
 				RX_MAX(HDLC_MAX_MRU), PCI_DMA_FROMDEVICE);
 				RX_MAX(HDLC_MAX_MRU), PCI_DMA_FROMDEVICE);
 			dev_kfree_skb(*skbuff);
 			dev_kfree_skb(*skbuff);
 		}
 		}
@@ -522,10 +524,10 @@ static inline int try_get_rx_skb(struct dscc4_dev_priv *dpriv,
 	dpriv->rx_skbuff[dirty] = skb;
 	dpriv->rx_skbuff[dirty] = skb;
 	if (skb) {
 	if (skb) {
 		skb->protocol = hdlc_type_trans(skb, dev);
 		skb->protocol = hdlc_type_trans(skb, dev);
-		rx_fd->data = pci_map_single(dpriv->pci_priv->pdev, skb->data,
-					     len, PCI_DMA_FROMDEVICE);
+		rx_fd->data = cpu_to_le32(pci_map_single(dpriv->pci_priv->pdev,
+					  skb->data, len, PCI_DMA_FROMDEVICE));
 	} else {
 	} else {
-		rx_fd->data = (u32) NULL;
+		rx_fd->data = 0;
 		ret = -1;
 		ret = -1;
 	}
 	}
 	return ret;
 	return ret;
@@ -587,7 +589,7 @@ static inline int dscc4_xpr_ack(struct dscc4_dev_priv *dpriv)
 
 
 	do {
 	do {
 		if (!(dpriv->flags & (NeedIDR | NeedIDT)) ||
 		if (!(dpriv->flags & (NeedIDR | NeedIDT)) ||
-		    (dpriv->iqtx[cur] & Xpr))
+		    (dpriv->iqtx[cur] & cpu_to_le32(Xpr)))
 			break;
 			break;
 		smp_rmb();
 		smp_rmb();
 		schedule_timeout_uninterruptible(10);
 		schedule_timeout_uninterruptible(10);
@@ -650,8 +652,9 @@ static inline void dscc4_rx_skb(struct dscc4_dev_priv *dpriv,
 		printk(KERN_DEBUG "%s: skb=0 (%s)\n", dev->name, __FUNCTION__);
 		printk(KERN_DEBUG "%s: skb=0 (%s)\n", dev->name, __FUNCTION__);
 		goto refill;
 		goto refill;
 	}
 	}
-	pkt_len = TO_SIZE(rx_fd->state2);
-	pci_unmap_single(pdev, rx_fd->data, RX_MAX(HDLC_MAX_MRU), PCI_DMA_FROMDEVICE);
+	pkt_len = TO_SIZE(le32_to_cpu(rx_fd->state2));
+	pci_unmap_single(pdev, le32_to_cpu(rx_fd->data),
+			 RX_MAX(HDLC_MAX_MRU), PCI_DMA_FROMDEVICE);
 	if ((skb->data[--pkt_len] & FrameOk) == FrameOk) {
 	if ((skb->data[--pkt_len] & FrameOk) == FrameOk) {
 		stats->rx_packets++;
 		stats->rx_packets++;
 		stats->rx_bytes += pkt_len;
 		stats->rx_bytes += pkt_len;
@@ -679,7 +682,7 @@ refill:
 	}
 	}
 	dscc4_rx_update(dpriv, dev);
 	dscc4_rx_update(dpriv, dev);
 	rx_fd->state2 = 0x00000000;
 	rx_fd->state2 = 0x00000000;
-	rx_fd->end = 0xbabeface;
+	rx_fd->end = cpu_to_le32(0xbabeface);
 }
 }
 
 
 static void dscc4_free1(struct pci_dev *pdev)
 static void dscc4_free1(struct pci_dev *pdev)
@@ -772,8 +775,8 @@ static int __devinit dscc4_init_one(struct pci_dev *pdev,
 	}
 	}
 	/* Global interrupt queue */
 	/* Global interrupt queue */
 	writel((u32)(((IRQ_RING_SIZE >> 5) - 1) << 20), ioaddr + IQLENR1);
 	writel((u32)(((IRQ_RING_SIZE >> 5) - 1) << 20), ioaddr + IQLENR1);
-	priv->iqcfg = (u32 *) pci_alloc_consistent(pdev,
-		IRQ_RING_SIZE*sizeof(u32), &priv->iqcfg_dma);
+	priv->iqcfg = (__le32 *) pci_alloc_consistent(pdev,
+		IRQ_RING_SIZE*sizeof(__le32), &priv->iqcfg_dma);
 	if (!priv->iqcfg)
 	if (!priv->iqcfg)
 		goto err_free_irq_5;
 		goto err_free_irq_5;
 	writel(priv->iqcfg_dma, ioaddr + IQCFG);
 	writel(priv->iqcfg_dma, ioaddr + IQCFG);
@@ -786,7 +789,7 @@ static int __devinit dscc4_init_one(struct pci_dev *pdev,
 	 */
 	 */
 	for (i = 0; i < dev_per_card; i++) {
 	for (i = 0; i < dev_per_card; i++) {
 		dpriv = priv->root + i;
 		dpriv = priv->root + i;
-		dpriv->iqtx = (u32 *) pci_alloc_consistent(pdev,
+		dpriv->iqtx = (__le32 *) pci_alloc_consistent(pdev,
 			IRQ_RING_SIZE*sizeof(u32), &dpriv->iqtx_dma);
 			IRQ_RING_SIZE*sizeof(u32), &dpriv->iqtx_dma);
 		if (!dpriv->iqtx)
 		if (!dpriv->iqtx)
 			goto err_free_iqtx_6;
 			goto err_free_iqtx_6;
@@ -794,7 +797,7 @@ static int __devinit dscc4_init_one(struct pci_dev *pdev,
 	}
 	}
 	for (i = 0; i < dev_per_card; i++) {
 	for (i = 0; i < dev_per_card; i++) {
 		dpriv = priv->root + i;
 		dpriv = priv->root + i;
-		dpriv->iqrx = (u32 *) pci_alloc_consistent(pdev,
+		dpriv->iqrx = (__le32 *) pci_alloc_consistent(pdev,
 			IRQ_RING_SIZE*sizeof(u32), &dpriv->iqrx_dma);
 			IRQ_RING_SIZE*sizeof(u32), &dpriv->iqrx_dma);
 		if (!dpriv->iqrx)
 		if (!dpriv->iqrx)
 			goto err_free_iqrx_7;
 			goto err_free_iqrx_7;
@@ -1156,8 +1159,8 @@ static int dscc4_start_xmit(struct sk_buff *skb, struct net_device *dev)
 	dpriv->tx_skbuff[next] = skb;
 	dpriv->tx_skbuff[next] = skb;
 	tx_fd = dpriv->tx_fd + next;
 	tx_fd = dpriv->tx_fd + next;
 	tx_fd->state = FrameEnd | TO_STATE_TX(skb->len);
 	tx_fd->state = FrameEnd | TO_STATE_TX(skb->len);
-	tx_fd->data = pci_map_single(ppriv->pdev, skb->data, skb->len,
-				     PCI_DMA_TODEVICE);
+	tx_fd->data = cpu_to_le32(pci_map_single(ppriv->pdev, skb->data, skb->len,
+				     PCI_DMA_TODEVICE));
 	tx_fd->complete = 0x00000000;
 	tx_fd->complete = 0x00000000;
 	tx_fd->jiffies = jiffies;
 	tx_fd->jiffies = jiffies;
 	mb();
 	mb();
@@ -1508,7 +1511,7 @@ static irqreturn_t dscc4_irq(int irq, void *token)
 	if (state & Cfg) {
 	if (state & Cfg) {
 		if (debug > 0)
 		if (debug > 0)
 			printk(KERN_DEBUG "%s: CfgIV\n", DRV_NAME);
 			printk(KERN_DEBUG "%s: CfgIV\n", DRV_NAME);
-		if (priv->iqcfg[priv->cfg_cur++%IRQ_RING_SIZE] & Arf)
+		if (priv->iqcfg[priv->cfg_cur++%IRQ_RING_SIZE] & cpu_to_le32(Arf))
 			printk(KERN_ERR "%s: %s failed\n", dev->name, "CFG");
 			printk(KERN_ERR "%s: %s failed\n", dev->name, "CFG");
 		if (!(state &= ~Cfg))
 		if (!(state &= ~Cfg))
 			goto out;
 			goto out;
@@ -1541,7 +1544,7 @@ static void dscc4_tx_irq(struct dscc4_pci_priv *ppriv,
 
 
 try:
 try:
 	cur = dpriv->iqtx_current%IRQ_RING_SIZE;
 	cur = dpriv->iqtx_current%IRQ_RING_SIZE;
-	state = dpriv->iqtx[cur];
+	state = le32_to_cpu(dpriv->iqtx[cur]);
 	if (!state) {
 	if (!state) {
 		if (debug > 4)
 		if (debug > 4)
 			printk(KERN_DEBUG "%s: Tx ISR = 0x%08x\n", dev->name,
 			printk(KERN_DEBUG "%s: Tx ISR = 0x%08x\n", dev->name,
@@ -1580,7 +1583,7 @@ try:
 			tx_fd = dpriv->tx_fd + cur;
 			tx_fd = dpriv->tx_fd + cur;
 			skb = dpriv->tx_skbuff[cur];
 			skb = dpriv->tx_skbuff[cur];
 			if (skb) {
 			if (skb) {
-				pci_unmap_single(ppriv->pdev, tx_fd->data,
+				pci_unmap_single(ppriv->pdev, le32_to_cpu(tx_fd->data),
 						 skb->len, PCI_DMA_TODEVICE);
 						 skb->len, PCI_DMA_TODEVICE);
 				if (tx_fd->state & FrameEnd) {
 				if (tx_fd->state & FrameEnd) {
 					stats->tx_packets++;
 					stats->tx_packets++;
@@ -1711,7 +1714,7 @@ static void dscc4_rx_irq(struct dscc4_pci_priv *priv,
 
 
 try:
 try:
 	cur = dpriv->iqrx_current%IRQ_RING_SIZE;
 	cur = dpriv->iqrx_current%IRQ_RING_SIZE;
-	state = dpriv->iqrx[cur];
+	state = le32_to_cpu(dpriv->iqrx[cur]);
 	if (!state)
 	if (!state)
 		return;
 		return;
 	dpriv->iqrx[cur] = 0;
 	dpriv->iqrx[cur] = 0;
@@ -1755,7 +1758,7 @@ try:
 					goto try;
 					goto try;
 				rx_fd->state1 &= ~Hold;
 				rx_fd->state1 &= ~Hold;
 				rx_fd->state2 = 0x00000000;
 				rx_fd->state2 = 0x00000000;
-				rx_fd->end = 0xbabeface;
+				rx_fd->end = cpu_to_le32(0xbabeface);
 			//}
 			//}
 			goto try;
 			goto try;
 		}
 		}
@@ -1834,7 +1837,7 @@ try:
 					hdlc_stats(dev)->rx_over_errors++;
 					hdlc_stats(dev)->rx_over_errors++;
 					rx_fd->state1 |= Hold;
 					rx_fd->state1 |= Hold;
 					rx_fd->state2 = 0x00000000;
 					rx_fd->state2 = 0x00000000;
-					rx_fd->end = 0xbabeface;
+					rx_fd->end = cpu_to_le32(0xbabeface);
 				} else
 				} else
 					dscc4_rx_skb(dpriv, dev);
 					dscc4_rx_skb(dpriv, dev);
 			} while (1);
 			} while (1);
@@ -1904,8 +1907,9 @@ static struct sk_buff *dscc4_init_dummy_skb(struct dscc4_dev_priv *dpriv)
 		skb_copy_to_linear_data(skb, version,
 		skb_copy_to_linear_data(skb, version,
 					strlen(version) % DUMMY_SKB_SIZE);
 					strlen(version) % DUMMY_SKB_SIZE);
 		tx_fd->state = FrameEnd | TO_STATE_TX(DUMMY_SKB_SIZE);
 		tx_fd->state = FrameEnd | TO_STATE_TX(DUMMY_SKB_SIZE);
-		tx_fd->data = pci_map_single(dpriv->pci_priv->pdev, skb->data,
-					     DUMMY_SKB_SIZE, PCI_DMA_TODEVICE);
+		tx_fd->data = cpu_to_le32(pci_map_single(dpriv->pci_priv->pdev,
+					     skb->data, DUMMY_SKB_SIZE,
+					     PCI_DMA_TODEVICE));
 		dpriv->tx_skbuff[last] = skb;
 		dpriv->tx_skbuff[last] = skb;
 	}
 	}
 	return skb;
 	return skb;
@@ -1937,8 +1941,8 @@ static int dscc4_init_ring(struct net_device *dev)
 		tx_fd->state = FrameEnd | TO_STATE_TX(2*DUMMY_SKB_SIZE);
 		tx_fd->state = FrameEnd | TO_STATE_TX(2*DUMMY_SKB_SIZE);
 		tx_fd->complete = 0x00000000;
 		tx_fd->complete = 0x00000000;
 	        /* FIXME: NULL should be ok - to be tried */
 	        /* FIXME: NULL should be ok - to be tried */
-	        tx_fd->data = dpriv->tx_fd_dma;
-		(tx_fd++)->next = (u32)(dpriv->tx_fd_dma +
+	        tx_fd->data = cpu_to_le32(dpriv->tx_fd_dma);
+		(tx_fd++)->next = cpu_to_le32(dpriv->tx_fd_dma +
 					(++i%TX_RING_SIZE)*sizeof(*tx_fd));
 					(++i%TX_RING_SIZE)*sizeof(*tx_fd));
 	} while (i < TX_RING_SIZE);
 	} while (i < TX_RING_SIZE);
 
 
@@ -1951,12 +1955,12 @@ static int dscc4_init_ring(struct net_device *dev)
 		/* size set by the host. Multiple of 4 bytes please */
 		/* size set by the host. Multiple of 4 bytes please */
 	        rx_fd->state1 = HiDesc;
 	        rx_fd->state1 = HiDesc;
 	        rx_fd->state2 = 0x00000000;
 	        rx_fd->state2 = 0x00000000;
-	        rx_fd->end = 0xbabeface;
+	        rx_fd->end = cpu_to_le32(0xbabeface);
 	        rx_fd->state1 |= TO_STATE_RX(HDLC_MAX_MRU);
 	        rx_fd->state1 |= TO_STATE_RX(HDLC_MAX_MRU);
 		// FIXME: return value verifiee mais traitement suspect
 		// FIXME: return value verifiee mais traitement suspect
 		if (try_get_rx_skb(dpriv, dev) >= 0)
 		if (try_get_rx_skb(dpriv, dev) >= 0)
 			dpriv->rx_dirty++;
 			dpriv->rx_dirty++;
-		(rx_fd++)->next = (u32)(dpriv->rx_fd_dma +
+		(rx_fd++)->next = cpu_to_le32(dpriv->rx_fd_dma +
 					(++i%RX_RING_SIZE)*sizeof(*rx_fd));
 					(++i%RX_RING_SIZE)*sizeof(*rx_fd));
 	} while (i < RX_RING_SIZE);
 	} while (i < RX_RING_SIZE);
 
 

+ 2 - 10
drivers/net/wan/lmc/lmc_media.c

@@ -890,16 +890,8 @@ write_av9110 (lmc_softc_t * sc, u_int32_t n, u_int32_t m, u_int32_t v,
 static void
 static void
 lmc_ssi_watchdog (lmc_softc_t * const sc)
 lmc_ssi_watchdog (lmc_softc_t * const sc)
 {
 {
-  u_int16_t mii17;
-  struct ssicsr2
-  {
-    unsigned short dtr:1, dsr:1, rts:1, cable:3, crc:1, led0:1, led1:1,
-      led2:1, led3:1, fifo:1, ll:1, rl:1, tm:1, loop:1;
-  };
-  struct ssicsr2 *ssicsr;
-  mii17 = lmc_mii_readreg (sc, 0, 17);
-  ssicsr = (struct ssicsr2 *) &mii17;
-  if (ssicsr->cable == 7)
+  u_int16_t mii17 = lmc_mii_readreg (sc, 0, 17);
+  if (((mii17 >> 3) & 7) == 7)
     {
     {
       lmc_led_off (sc, LMC_MII16_LED2);
       lmc_led_off (sc, LMC_MII16_LED2);
     }
     }

+ 9 - 3
drivers/net/wan/sbni.h

@@ -44,9 +44,15 @@ enum {
 #define PR_RES 0x80
 #define PR_RES 0x80
 
 
 struct sbni_csr1 {
 struct sbni_csr1 {
-	unsigned rxl	: 5;
-	unsigned rate	: 2;
-	unsigned 	: 1;
+#ifdef __LITTLE_ENDIAN_BITFIELD
+	u8 rxl	: 5;
+	u8 rate	: 2;
+	u8 	: 1;
+#else
+	u8 	: 1;
+	u8 rate	: 2;
+	u8 rxl	: 5;
+#endif
 };
 };
 
 
 /* fields in frame header */
 /* fields in frame header */

+ 6 - 5
drivers/net/wireless/b43/rfkill.c

@@ -138,8 +138,11 @@ void b43_rfkill_init(struct b43_wldev *dev)
 	rfk->rfkill->user_claim_unsupported = 1;
 	rfk->rfkill->user_claim_unsupported = 1;
 
 
 	rfk->poll_dev = input_allocate_polled_device();
 	rfk->poll_dev = input_allocate_polled_device();
-	if (!rfk->poll_dev)
-		goto err_free_rfk;
+	if (!rfk->poll_dev) {
+		rfkill_free(rfk->rfkill);
+		goto err_freed_rfk;
+	}
+
 	rfk->poll_dev->private = dev;
 	rfk->poll_dev->private = dev;
 	rfk->poll_dev->poll = b43_rfkill_poll;
 	rfk->poll_dev->poll = b43_rfkill_poll;
 	rfk->poll_dev->poll_interval = 1000; /* msecs */
 	rfk->poll_dev->poll_interval = 1000; /* msecs */
@@ -175,8 +178,7 @@ err_unreg_rfk:
 err_free_polldev:
 err_free_polldev:
 	input_free_polled_device(rfk->poll_dev);
 	input_free_polled_device(rfk->poll_dev);
 	rfk->poll_dev = NULL;
 	rfk->poll_dev = NULL;
-err_free_rfk:
-	rfkill_free(rfk->rfkill);
+err_freed_rfk:
 	rfk->rfkill = NULL;
 	rfk->rfkill = NULL;
 out_error:
 out_error:
 	rfk->registered = 0;
 	rfk->registered = 0;
@@ -195,6 +197,5 @@ void b43_rfkill_exit(struct b43_wldev *dev)
 	rfkill_unregister(rfk->rfkill);
 	rfkill_unregister(rfk->rfkill);
 	input_free_polled_device(rfk->poll_dev);
 	input_free_polled_device(rfk->poll_dev);
 	rfk->poll_dev = NULL;
 	rfk->poll_dev = NULL;
-	rfkill_free(rfk->rfkill);
 	rfk->rfkill = NULL;
 	rfk->rfkill = NULL;
 }
 }

+ 3 - 3
drivers/net/wireless/hostap/hostap_plx.c

@@ -608,7 +608,7 @@ static void prism2_plx_remove(struct pci_dev *pdev)
 
 
 MODULE_DEVICE_TABLE(pci, prism2_plx_id_table);
 MODULE_DEVICE_TABLE(pci, prism2_plx_id_table);
 
 
-static struct pci_driver prism2_plx_drv_id = {
+static struct pci_driver prism2_plx_driver = {
 	.name		= "hostap_plx",
 	.name		= "hostap_plx",
 	.id_table	= prism2_plx_id_table,
 	.id_table	= prism2_plx_id_table,
 	.probe		= prism2_plx_probe,
 	.probe		= prism2_plx_probe,
@@ -618,13 +618,13 @@ static struct pci_driver prism2_plx_drv_id = {
 
 
 static int __init init_prism2_plx(void)
 static int __init init_prism2_plx(void)
 {
 {
-	return pci_register_driver(&prism2_plx_drv_id);
+	return pci_register_driver(&prism2_plx_driver);
 }
 }
 
 
 
 
 static void __exit exit_prism2_plx(void)
 static void __exit exit_prism2_plx(void)
 {
 {
-	pci_unregister_driver(&prism2_plx_drv_id);
+	pci_unregister_driver(&prism2_plx_driver);
 }
 }
 
 
 
 

+ 1 - 1
drivers/net/wireless/ipw2200.c

@@ -4935,7 +4935,7 @@ static int ipw_queue_reset(struct ipw_priv *priv)
 /**
 /**
  * Reclaim Tx queue entries no more used by NIC.
  * Reclaim Tx queue entries no more used by NIC.
  *
  *
- * When FW adwances 'R' index, all entries between old and
+ * When FW advances 'R' index, all entries between old and
  * new 'R' index need to be reclaimed. As result, some free space
  * new 'R' index need to be reclaimed. As result, some free space
  * forms. If there is enough free space (> low mark), wake Tx queue.
  * forms. If there is enough free space (> low mark), wake Tx queue.
  *
  *

+ 4 - 0
drivers/net/wireless/libertas/if_sdio.c

@@ -871,6 +871,10 @@ static int if_sdio_probe(struct sdio_func *func,
 		if (sscanf(func->card->info[i],
 		if (sscanf(func->card->info[i],
 				"ID: %x", &model) == 1)
 				"ID: %x", &model) == 1)
 			break;
 			break;
+               if (!strcmp(func->card->info[i], "IBIS Wireless SDIO Card")) {
+                       model = 4;
+                       break;
+               }
 	}
 	}
 
 
 	if (i == func->card->num_info) {
 	if (i == func->card->num_info) {

+ 1 - 1
drivers/net/wireless/rt2x00/rt2x00pci.c

@@ -149,7 +149,7 @@ void rt2x00pci_rxdone(struct rt2x00_dev *rt2x00dev)
 		 * The data behind the ieee80211 header must be
 		 * The data behind the ieee80211 header must be
 		 * aligned on a 4 byte boundary.
 		 * aligned on a 4 byte boundary.
 		 */
 		 */
-		align = NET_IP_ALIGN + (2 * (header_size % 4 == 0));
+		align = header_size % 4;
 
 
 		/*
 		/*
 		 * Allocate the sk_buffer, initialize it and copy
 		 * Allocate the sk_buffer, initialize it and copy

+ 9 - 2
drivers/net/wireless/rt2x00/rt2x00usb.c

@@ -245,13 +245,20 @@ static void rt2x00usb_interrupt_rxdone(struct urb *urb)
 	 * Allocate a new sk buffer to replace the current one.
 	 * Allocate a new sk buffer to replace the current one.
 	 * If allocation fails, we should drop the current frame
 	 * If allocation fails, we should drop the current frame
 	 * so we can recycle the existing sk buffer for the new frame.
 	 * so we can recycle the existing sk buffer for the new frame.
+	 * As alignment we use 2 and not NET_IP_ALIGN because we need
+	 * to be sure we have 2 bytes room in the head. (NET_IP_ALIGN
+	 * can be 0 on some hardware). We use these 2 bytes for frame
+	 * alignment later, we assume that the chance that
+	 * header_size % 4 == 2 is bigger then header_size % 2 == 0
+	 * and thus optimize alignment by reserving the 2 bytes in
+	 * advance.
 	 */
 	 */
 	frame_size = entry->ring->data_size + entry->ring->desc_size;
 	frame_size = entry->ring->data_size + entry->ring->desc_size;
-	skb = dev_alloc_skb(frame_size + NET_IP_ALIGN);
+	skb = dev_alloc_skb(frame_size + 2);
 	if (!skb)
 	if (!skb)
 		goto skip_entry;
 		goto skip_entry;
 
 
-	skb_reserve(skb, NET_IP_ALIGN);
+	skb_reserve(skb, 2);
 	skb_put(skb, frame_size);
 	skb_put(skb, frame_size);
 
 
 	/*
 	/*