From dcc997738e538919101d8756f19ca23110b25d8d Mon Sep 17 00:00:00 2001 From: Stephen Hemminger Date: Wed, 14 May 2008 22:33:38 -0700 Subject: net: handle errors from device_rename device_rename can fail with -EEXIST or -ENOMEM, so handle any problems. Signed-off-by: Stephen Hemminger Signed-off-by: David S. Miller diff --git a/net/core/dev.c b/net/core/dev.c index a1607bc..ce88c0d 100644 --- a/net/core/dev.c +++ b/net/core/dev.c @@ -903,7 +903,11 @@ int dev_change_name(struct net_device *dev, char *newname) strlcpy(dev->name, newname, IFNAMSIZ); rollback: - device_rename(&dev->dev, dev->name); + err = device_rename(&dev->dev, dev->name); + if (err) { + memcpy(dev->name, oldname, IFNAMSIZ); + return err; + } write_lock_bh(&dev_base_lock); hlist_del(&dev->name_hlist); -- cgit v0.10.2 From 0599ad53fee2d084f9ba26247d7452f06a40d298 Mon Sep 17 00:00:00 2001 From: Stephen Hemminger Date: Wed, 14 May 2008 22:34:16 -0700 Subject: sysfs: remove error messages for -EEXIST case It is possible that the entry in sysfs already exists, one case of this is when a network device is renamed to bonding_masters. Anyway, in this case the proper error path is for device_rename to return an error code, not to generate bogus backtrace and errors. Also, to avoid possible races, the create link should be done before the remove link. This makes a device rename atomic operation like other renames. Signed-off-by: Stephen Hemminger Signed-off-by: Greg Kroah-Hartman Signed-off-by: David S. Miller diff --git a/drivers/base/core.c b/drivers/base/core.c index be288b5..3eeac5a 100644 --- a/drivers/base/core.c +++ b/drivers/base/core.c @@ -1218,13 +1218,11 @@ int device_rename(struct device *dev, char *new_name) } #else if (dev->class) { - sysfs_remove_link(&dev->class->subsys.kobj, old_device_name); error = sysfs_create_link(&dev->class->subsys.kobj, &dev->kobj, dev->bus_id); - if (error) { - dev_err(dev, "%s: sysfs_create_symlink failed (%d)\n", - __func__, error); - } + if (error) + goto out; + sysfs_remove_link(&dev->class->subsys.kobj, old_device_name); } #endif diff --git a/fs/sysfs/dir.c b/fs/sysfs/dir.c index a1c3a1f..8c0e4b9 100644 --- a/fs/sysfs/dir.c +++ b/fs/sysfs/dir.c @@ -419,12 +419,8 @@ void sysfs_addrm_start(struct sysfs_addrm_cxt *acxt, */ int sysfs_add_one(struct sysfs_addrm_cxt *acxt, struct sysfs_dirent *sd) { - if (sysfs_find_dirent(acxt->parent_sd, sd->s_name)) { - printk(KERN_WARNING "sysfs: duplicate filename '%s' " - "can not be created\n", sd->s_name); - WARN_ON(1); + if (sysfs_find_dirent(acxt->parent_sd, sd->s_name)) return -EEXIST; - } sd->s_parent = sysfs_get(acxt->parent_sd); -- cgit v0.10.2 From 38d2f38be9e4a2f1e3324c973a903aa972f71d0f Mon Sep 17 00:00:00 2001 From: Stephen Hemminger Date: Wed, 14 May 2008 22:35:04 -0700 Subject: bonding: handle case of device named bonding_master If device already exists named bonding_masters, then fail. This is a wierd corner case only a QA group could love. Signed-off-by: Stephen Hemminger Signed-off-by: David S. Miller diff --git a/drivers/net/bonding/bond_sysfs.c b/drivers/net/bonding/bond_sysfs.c index 68c41a0..08f3d39 100644 --- a/drivers/net/bonding/bond_sysfs.c +++ b/drivers/net/bonding/bond_sysfs.c @@ -1437,8 +1437,16 @@ int bond_create_sysfs(void) * configure multiple bonding devices. */ if (ret == -EEXIST) { - netdev_class = NULL; - return 0; + /* Is someone being kinky and naming a device bonding_master? */ + if (__dev_get_by_name(&init_net, + class_attr_bonding_masters.attr.name)) + printk(KERN_ERR + "network device named %s already exists in sysfs", + class_attr_bonding_masters.attr.name); + else { + netdev_class = NULL; + return 0; + } } return ret; -- cgit v0.10.2 From a1a61a435b3cc157830b7d42b175151ae5eabdd3 Mon Sep 17 00:00:00 2001 From: Mike Frysinger Date: Wed, 14 May 2008 23:24:09 -0700 Subject: atm: Cleanup atm_tcp.h and atm.h for userspace. The atm_tcp.h uses types from linux/atm.h, but does not include it. It should also use the standard __u## types from linux/types.h rather than the uint##_t types since the former can be found with the kernel already. Same goes for linux/atm.h. The linux/socket.h include there also gets dropped as atm.h does not actually use anything from socket.h. Signed-off-by: Mike Frysinger Signed-off-by: Andrew Morton Signed-off-by: David S. Miller diff --git a/include/linux/atm.h b/include/linux/atm.h index 60136684..c791ddd 100644 --- a/include/linux/atm.h +++ b/include/linux/atm.h @@ -16,14 +16,11 @@ * documentation. Do not change them. */ -#ifdef __KERNEL__ -#include -#include -#endif #include #include #include #include +#include /* general ATM constants */ @@ -212,7 +209,7 @@ struct sockaddr_atmsvc { char pub[ATM_E164_LEN+1]; /* public address (E.164) */ /* unused addresses must be bzero'ed */ char lij_type; /* role in LIJ call; one of ATM_LIJ* */ - uint32_t lij_id; /* LIJ call identifier */ + __u32 lij_id; /* LIJ call identifier */ } sas_addr __ATM_API_ALIGN; /* SVC address */ }; diff --git a/include/linux/atm_tcp.h b/include/linux/atm_tcp.h index 18787f9..375638f 100644 --- a/include/linux/atm_tcp.h +++ b/include/linux/atm_tcp.h @@ -8,11 +8,9 @@ #define LINUX_ATM_TCP_H #include - -#ifdef __KERNEL__ -#include -#endif +#include #include +#include /* @@ -20,9 +18,9 @@ */ struct atmtcp_hdr { - uint16_t vpi; - uint16_t vci; - uint32_t length; /* ... of data part */ + __u16 vpi; + __u16 vci; + __u32 length; /* ... of data part */ }; /* -- cgit v0.10.2 From a9dd7fe28742c6b22eb8f214a04c4d2bcb2c0899 Mon Sep 17 00:00:00 2001 From: Mark Asselstine Date: Wed, 14 May 2008 23:25:33 -0700 Subject: hysdn: Remove cli()/sti() calls. The use of cli()/sti() within the do/while was a way to ensure interrupts were only disabled for short periods of time while the bulk of the time interrupts were free to occur. The use of the spin lock has eliminated the need to play with interrupts in this way while still allowing for IO to be protected. The remaining 3 sti() calls seem unneeded now that at no other point in the driver is there a call to cli(). Signed-off-by: Mark Asselstine Acked-by: Karsten Keil Signed-off-by: Andrew Morton Signed-off-by: David S. Miller diff --git a/drivers/isdn/hysdn/boardergo.c b/drivers/isdn/hysdn/boardergo.c index 6cdbad3..3eb096f 100644 --- a/drivers/isdn/hysdn/boardergo.c +++ b/drivers/isdn/hysdn/boardergo.c @@ -64,10 +64,11 @@ ergo_interrupt(int intno, void *dev_id) } /* ergo_interrupt */ /******************************************************************************/ -/* ergo_irq_bh is the function called by the immediate kernel task list after */ -/* being activated with queue_task and no interrupts active. This task is the */ -/* only one handling data transfer from or to the card after booting. The task */ -/* may be queued from everywhere (interrupts included). */ +/* ergo_irq_bh will be called as part of the kernel clearing its shared work */ +/* queue sometime after a call to schedule_work has been made passing our */ +/* work_struct. This task is the only one handling data transfer from or to */ +/* the card after booting. The task may be queued from everywhere */ +/* (interrupts included). */ /******************************************************************************/ static void ergo_irq_bh(struct work_struct *ugli_api) @@ -90,7 +91,6 @@ ergo_irq_bh(struct work_struct *ugli_api) card->hw_lock = 1; /* we now lock the hardware */ do { - sti(); /* reenable other ints */ again = 0; /* assume loop not to be repeated */ if (!dpr->ToHyFlag) { @@ -110,7 +110,6 @@ ergo_irq_bh(struct work_struct *ugli_api) again = 1; /* restart loop */ } } /* a message has arrived for us */ - cli(); /* no further ints */ if (again) { dpr->ToHyInt = 1; dpr->ToPcInt = 1; /* interrupt to E1 for all cards */ @@ -242,7 +241,6 @@ ergo_writebootimg(struct HYSDN_CARD *card, unsigned char *buf, byteout(card->iobase + PCI9050_USER_IO, PCI9050_E1_RUN); /* start E1 processor */ /* the interrupts are still masked */ - sti(); msleep_interruptible(20); /* Timeout 20ms */ if (((tDpramBootSpooler *) card->dpram)->Len != DPRAM_SPOOLER_DATA_SIZE) { @@ -276,7 +274,6 @@ ergo_writebootseq(struct HYSDN_CARD *card, unsigned char *buf, int len) dst = sp->Data; /* point to data in spool structure */ buflen = sp->Len; /* maximum len of spooled data */ wr_mirror = sp->WrPtr; /* only once read */ - sti(); /* try until all bytes written or error */ i = 0x1000; /* timeout value */ @@ -380,7 +377,6 @@ ergo_waitpofready(struct HYSDN_CARD *card) #endif /* CONFIG_HYSDN_CAPI */ return (0); /* success */ } /* data has arrived */ - sti(); msleep_interruptible(50); /* Timeout 50ms */ } /* wait until timeout */ -- cgit v0.10.2 From 01bbf2c7ddc93479eecebf8495848c0f362130c5 Mon Sep 17 00:00:00 2001 From: Andrew Morton Date: Wed, 14 May 2008 23:27:18 -0700 Subject: hysdn: No longer broken on SMP. With the cli/sti code sorted out we think this driver is OK for use on SMP systems. Acked-by: Mark Asselstine Acked-by: Karsten Keil Signed-off-by: Andrew Morton Signed-off-by: David S. Miller diff --git a/drivers/isdn/hysdn/Kconfig b/drivers/isdn/hysdn/Kconfig index c6d8a70..c9e4231 100644 --- a/drivers/isdn/hysdn/Kconfig +++ b/drivers/isdn/hysdn/Kconfig @@ -3,7 +3,7 @@ # config HYSDN tristate "Hypercope HYSDN cards (Champ, Ergo, Metro) support (module only)" - depends on m && PROC_FS && PCI && BROKEN_ON_SMP + depends on m && PROC_FS && PCI help Say Y here if you have one of Hypercope's active PCI ISDN cards Champ, Ergo and Metro. You will then get a module called hysdn. -- cgit v0.10.2 From ffd8211fb18e1052b2d9eded629cc3c0b872d06a Mon Sep 17 00:00:00 2001 From: Alan Cox Date: Wed, 14 May 2008 23:28:47 -0700 Subject: iphase: Fix 64bit warning. Time is unsigned long (except when you are in a hurry) so we need to store rx_tmp_jif in the right sized object. Signed-off-by: Alan Cox Signed-off-by: Andrew Morton Signed-off-by: David S. Miller diff --git a/drivers/atm/iphase.h b/drivers/atm/iphase.h index 133eefc..b2cd20f 100644 --- a/drivers/atm/iphase.h +++ b/drivers/atm/iphase.h @@ -1025,7 +1025,8 @@ typedef struct iadev_t { spinlock_t rx_lock, misc_lock; struct atm_vcc **rx_open; /* list of all open VCs */ u16 num_rx_desc, rx_buf_sz, rxing; - u32 rx_pkt_ram, rx_tmp_cnt, rx_tmp_jif; + u32 rx_pkt_ram, rx_tmp_cnt; + unsigned long rx_tmp_jif; void __iomem *RX_DESC_BASE_ADDR; u32 drop_rxpkt, drop_rxcell, rx_cell_cnt, rx_pkt_cnt; struct atm_dev *next_board; /* other iphase devices */ -- cgit v0.10.2 From 066b2118976e6e7cc50eed39e2747c75343a23c4 Mon Sep 17 00:00:00 2001 From: Marcin Slusarz Date: Wed, 14 May 2008 23:30:06 -0700 Subject: isdn/capi: Return proper errnos on module init. cdebug_init() is called from kcapi_init() which is module initialization function, so it must return negative values on errors. Signed-off-by: Marcin Slusarz Acked-by: Karsten Keil Signed-off-by: Andrew Morton Signed-off-by: David S. Miller diff --git a/drivers/isdn/capi/capiutil.c b/drivers/isdn/capi/capiutil.c index ebef4ce..29419a8 100644 --- a/drivers/isdn/capi/capiutil.c +++ b/drivers/isdn/capi/capiutil.c @@ -948,17 +948,17 @@ int __init cdebug_init(void) { g_cmsg= kmalloc(sizeof(_cmsg), GFP_KERNEL); if (!g_cmsg) - return ENOMEM; + return -ENOMEM; g_debbuf = kmalloc(sizeof(_cdebbuf), GFP_KERNEL); if (!g_debbuf) { kfree(g_cmsg); - return ENOMEM; + return -ENOMEM; } g_debbuf->buf = kmalloc(CDEBUG_GSIZE, GFP_KERNEL); if (!g_debbuf->buf) { kfree(g_cmsg); kfree(g_debbuf); - return ENOMEM;; + return -ENOMEM;; } g_debbuf->size = CDEBUG_GSIZE; g_debbuf->buf[0] = 0; -- cgit v0.10.2 From 23f40dc650c0344b37fe54143868a31be66db882 Mon Sep 17 00:00:00 2001 From: Mathieu Chouquet-Stringer Date: Wed, 14 May 2008 19:03:18 -0400 Subject: hostap: fix "registers" registration in procfs The "registers" entry was incorrectly created in the procfs root instead of the device specific directory. Move "registers" registration immediately after the containing procfs directory is created. Signed-off-by: Mathieu Chouquet-Stringer Signed-off-by: Pavel Roskin Signed-off-by: John W. Linville diff --git a/drivers/net/wireless/hostap/hostap_hw.c b/drivers/net/wireless/hostap/hostap_hw.c index 7be68db..cdf90c4 100644 --- a/drivers/net/wireless/hostap/hostap_hw.c +++ b/drivers/net/wireless/hostap/hostap_hw.c @@ -3276,11 +3276,6 @@ while (0) } printk(KERN_INFO "%s: Registered netdevice %s\n", dev_info, dev->name); -#ifndef PRISM2_NO_PROCFS_DEBUG - create_proc_read_entry("registers", 0, local->proc, - prism2_registers_proc_read, local); -#endif /* PRISM2_NO_PROCFS_DEBUG */ - hostap_init_data(local); return dev; @@ -3307,6 +3302,10 @@ static int hostap_hw_ready(struct net_device *dev) netif_carrier_off(local->ddev); } hostap_init_proc(local); +#ifndef PRISM2_NO_PROCFS_DEBUG + create_proc_read_entry("registers", 0, local->proc, + prism2_registers_proc_read, local); +#endif /* PRISM2_NO_PROCFS_DEBUG */ hostap_init_ap_proc(local); return 0; } -- cgit v0.10.2 From 34a961f7db36f10abd6b153411fe8c810f21f6b3 Mon Sep 17 00:00:00 2001 From: Abhijeet Kolekar Date: Fri, 9 May 2008 09:35:41 -0700 Subject: mac80211 : Association with 11n hidden ssid ap. This patch fixes the association problem with 11n hidden ssid ap. Patch fixes the problem of associating with hidden ssid when all three parameters ap,essid and channel are given to iwconfig. This patch removes the condition of checking three parameters and always checks for bss in bss list while associating. Signed-off-by: Abhijeet Kolekar Signed-off-by: John W. Linville diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c index 4adba09..e470bf1 100644 --- a/net/mac80211/mlme.c +++ b/net/mac80211/mlme.c @@ -3446,21 +3446,17 @@ static int ieee80211_sta_config_auth(struct net_device *dev, struct ieee80211_sta_bss *bss, *selected = NULL; int top_rssi = 0, freq; - if (!(ifsta->flags & (IEEE80211_STA_AUTO_SSID_SEL | - IEEE80211_STA_AUTO_BSSID_SEL | IEEE80211_STA_AUTO_CHANNEL_SEL))) { - ifsta->state = IEEE80211_AUTHENTICATE; - ieee80211_sta_reset_auth(dev, ifsta); - return 0; - } - spin_lock_bh(&local->sta_bss_lock); freq = local->oper_channel->center_freq; list_for_each_entry(bss, &local->sta_bss_list, list) { if (!(bss->capability & WLAN_CAPABILITY_ESS)) continue; - if (!!(bss->capability & WLAN_CAPABILITY_PRIVACY) ^ - !!sdata->default_key) + if ((ifsta->flags & (IEEE80211_STA_AUTO_SSID_SEL | + IEEE80211_STA_AUTO_BSSID_SEL | + IEEE80211_STA_AUTO_CHANNEL_SEL)) && + (!!(bss->capability & WLAN_CAPABILITY_PRIVACY) ^ + !!sdata->default_key)) continue; if (!(ifsta->flags & IEEE80211_STA_AUTO_CHANNEL_SEL) && -- cgit v0.10.2 From 2f561feb386d6adefbad63c59a1fcd298ac6a79c Mon Sep 17 00:00:00 2001 From: Ivo van Doorn Date: Sat, 10 May 2008 13:40:49 +0200 Subject: mac80211: Add RTNL version of ieee80211_iterate_active_interfaces Since commit e38bad4766a110b61fa6038f10be16ced8c6cc38 mac80211: make ieee80211_iterate_active_interfaces not need rtnl rt2500usb and rt73usb broke down due to attempting register access in atomic context (which is not possible for USB hardware). This patch restores ieee80211_iterate_active_interfaces() to use RTNL lock, and provides the non-RTNL version under a new name: ieee80211_iterate_active_interfaces_atomic() So far only rt2x00 uses ieee80211_iterate_active_interfaces(), and those drivers require the RTNL version of ieee80211_iterate_active_interfaces(). Since they already call that function directly, this patch will automatically fix the USB rt2x00 drivers. v2: Rename ieee80211_iterate_active_interfaces_rtnl Signed-off-by: Ivo van Doorn Acked-by: Johannes Berg Signed-off-by: John W. Linville diff --git a/include/net/mac80211.h b/include/net/mac80211.h index 4a80d74..dae3f9e 100644 --- a/include/net/mac80211.h +++ b/include/net/mac80211.h @@ -1594,13 +1594,16 @@ void ieee80211_wake_queues(struct ieee80211_hw *hw); void ieee80211_scan_completed(struct ieee80211_hw *hw); /** - * ieee80211_iterate_active_interfaces - iterate active interfaces + * ieee80211_iterate_active_interfaces- iterate active interfaces * * This function iterates over the interfaces associated with a given * hardware that are currently active and calls the callback for them. + * This function allows the iterator function to sleep, when the iterator + * function is atomic @ieee80211_iterate_active_interfaces_atomic can + * be used. * * @hw: the hardware struct of which the interfaces should be iterated over - * @iterator: the iterator function to call, cannot sleep + * @iterator: the iterator function to call * @data: first argument of the iterator function */ void ieee80211_iterate_active_interfaces(struct ieee80211_hw *hw, @@ -1609,6 +1612,24 @@ void ieee80211_iterate_active_interfaces(struct ieee80211_hw *hw, void *data); /** + * ieee80211_iterate_active_interfaces_atomic - iterate active interfaces + * + * This function iterates over the interfaces associated with a given + * hardware that are currently active and calls the callback for them. + * This function requires the iterator callback function to be atomic, + * if that is not desired, use @ieee80211_iterate_active_interfaces instead. + * + * @hw: the hardware struct of which the interfaces should be iterated over + * @iterator: the iterator function to call, cannot sleep + * @data: first argument of the iterator function + */ +void ieee80211_iterate_active_interfaces_atomic(struct ieee80211_hw *hw, + void (*iterator)(void *data, + u8 *mac, + struct ieee80211_vif *vif), + void *data); + +/** * ieee80211_start_tx_ba_session - Start a tx Block Ack session. * @hw: pointer as obtained from ieee80211_alloc_hw(). * @ra: receiver address of the BA session recipient diff --git a/net/mac80211/util.c b/net/mac80211/util.c index 24a465c..131e9e6 100644 --- a/net/mac80211/util.c +++ b/net/mac80211/util.c @@ -389,6 +389,41 @@ void ieee80211_iterate_active_interfaces( struct ieee80211_local *local = hw_to_local(hw); struct ieee80211_sub_if_data *sdata; + rtnl_lock(); + + list_for_each_entry(sdata, &local->interfaces, list) { + switch (sdata->vif.type) { + case IEEE80211_IF_TYPE_INVALID: + case IEEE80211_IF_TYPE_MNTR: + case IEEE80211_IF_TYPE_VLAN: + continue; + case IEEE80211_IF_TYPE_AP: + case IEEE80211_IF_TYPE_STA: + case IEEE80211_IF_TYPE_IBSS: + case IEEE80211_IF_TYPE_WDS: + case IEEE80211_IF_TYPE_MESH_POINT: + break; + } + if (sdata->dev == local->mdev) + continue; + if (netif_running(sdata->dev)) + iterator(data, sdata->dev->dev_addr, + &sdata->vif); + } + + rtnl_unlock(); +} +EXPORT_SYMBOL_GPL(ieee80211_iterate_active_interfaces); + +void ieee80211_iterate_active_interfaces_atomic( + struct ieee80211_hw *hw, + void (*iterator)(void *data, u8 *mac, + struct ieee80211_vif *vif), + void *data) +{ + struct ieee80211_local *local = hw_to_local(hw); + struct ieee80211_sub_if_data *sdata; + rcu_read_lock(); list_for_each_entry_rcu(sdata, &local->interfaces, list) { @@ -413,4 +448,4 @@ void ieee80211_iterate_active_interfaces( rcu_read_unlock(); } -EXPORT_SYMBOL_GPL(ieee80211_iterate_active_interfaces); +EXPORT_SYMBOL_GPL(ieee80211_iterate_active_interfaces_atomic); -- cgit v0.10.2 From 02969d296e91626d9942ea15f8a95fe056025ef1 Mon Sep 17 00:00:00 2001 From: Brian Cavagnolo Date: Tue, 13 May 2008 13:54:59 +0100 Subject: libertas: fix command timeout after firmware failure This is a fix for OLPC ticket #6586: "SCAN command fails, timer doesn't fire". In fact, the timer was firing; the problem was that the dnld_sent state variable was not being updated after the timer expired, so lbs_execute_next_command was not being called. Signed-off-by: Brian Cavagnolo Signed-off-by: Javier Cardona Signed-off-by: David Woodhouse Signed-off-by: John W. Linville diff --git a/drivers/net/wireless/libertas/main.c b/drivers/net/wireless/libertas/main.c index 406f54d..bb08f0b 100644 --- a/drivers/net/wireless/libertas/main.c +++ b/drivers/net/wireless/libertas/main.c @@ -756,6 +756,7 @@ static int lbs_thread(void *data) priv->nr_retries = 0; } else { priv->cur_cmd = NULL; + priv->dnld_sent = DNLD_RES_RECEIVED; lbs_pr_info("requeueing command %x due to timeout (#%d)\n", le16_to_cpu(cmdnode->cmdbuf->command), priv->nr_retries); -- cgit v0.10.2 From b7acbdfbd1f277c1eb23f344f899cfa4cd0bf36a Mon Sep 17 00:00:00 2001 From: Roel Kluin Date: Tue, 13 May 2008 22:12:27 +0200 Subject: wireless, airo: waitbusy() won't delay There will be no delay even when COMMAND_BUSY (defined 0x8000) is set: 0x8000 & (delay < 10000) will evaluate to 0 - when delay is 0. Signed-off-by: Roel Kluin Signed-off-by: John W. Linville diff --git a/drivers/net/wireless/airo.c b/drivers/net/wireless/airo.c index 45f47c1..efb7444 100644 --- a/drivers/net/wireless/airo.c +++ b/drivers/net/wireless/airo.c @@ -2904,7 +2904,7 @@ EXPORT_SYMBOL(init_airo_card); static int waitbusy (struct airo_info *ai) { int delay = 0; - while ((IN4500 (ai, COMMAND) & COMMAND_BUSY) & (delay < 10000)) { + while ((IN4500 (ai, COMMAND) & COMMAND_BUSY) && (delay < 10000)) { udelay (10); if ((++delay % 20) == 0) OUT4500(ai, EVACK, EV_CLEARCOMMANDBUSY); -- cgit v0.10.2 From 229ce3abb6d6d4598de8ef1ed1e2da8163a9bbc0 Mon Sep 17 00:00:00 2001 From: Masakazu Mokuno Date: Wed, 14 May 2008 14:16:50 +0900 Subject: wireless: Create 'device' symlink in sysfs Some network interfaces of the wireless drivers lack the 'device' symlink in sysfs. This patch lets the drivers create the links. Signed-off-by: Masakazu Mokuno Acked-by: Dan Williams Signed-off-by: John W. Linville diff --git a/drivers/net/wireless/airo.c b/drivers/net/wireless/airo.c index efb7444..4e1c690 100644 --- a/drivers/net/wireless/airo.c +++ b/drivers/net/wireless/airo.c @@ -2668,6 +2668,7 @@ static struct net_device *init_wifidev(struct airo_info *ai, dev->irq = ethdev->irq; dev->base_addr = ethdev->base_addr; dev->wireless_data = ethdev->wireless_data; + SET_NETDEV_DEV(dev, ethdev->dev.parent); memcpy(dev->dev_addr, ethdev->dev_addr, dev->addr_len); err = register_netdev(dev); if (err<0) { diff --git a/drivers/net/wireless/ipw2200.c b/drivers/net/wireless/ipw2200.c index fa87c5c..d74c061 100644 --- a/drivers/net/wireless/ipw2200.c +++ b/drivers/net/wireless/ipw2200.c @@ -11584,6 +11584,7 @@ static int ipw_prom_alloc(struct ipw_priv *priv) priv->prom_net_dev->hard_start_xmit = ipw_prom_hard_start_xmit; priv->prom_priv->ieee->iw_mode = IW_MODE_MONITOR; + SET_NETDEV_DEV(priv->prom_net_dev, &priv->pci_dev->dev); rc = register_netdev(priv->prom_net_dev); if (rc) { diff --git a/drivers/net/wireless/libertas/main.c b/drivers/net/wireless/libertas/main.c index bb08f0b..e1f0660 100644 --- a/drivers/net/wireless/libertas/main.c +++ b/drivers/net/wireless/libertas/main.c @@ -1565,6 +1565,7 @@ static int lbs_add_rtap(struct lbs_private *priv) rtap_dev->hard_start_xmit = lbs_rtap_hard_start_xmit; rtap_dev->set_multicast_list = lbs_set_multicast_list; rtap_dev->priv = priv; + SET_NETDEV_DEV(rtap_dev, priv->dev->dev.parent); ret = register_netdev(rtap_dev); if (ret) { -- cgit v0.10.2 From 090c48d3dd5ea90b37350334aaed9a93b0c1e0a1 Mon Sep 17 00:00:00 2001 From: James Chapman Date: Mon, 19 May 2008 14:10:01 -0700 Subject: l2tp: avoid skb truesize bug if headroom is increased A user reported seeing occasional bugs such as the following when using the L2TP driver. SKB BUG: Invalid truesize (272) len=72, sizeof(sk_buff)=208 When L2TP adds its header in the transmit path, it might need to increase the headroom of the skb. In some cases, the increased headroom trips a kernel bug when the skb is freed because the skb has grown beyond its truesize value. The fix is to increase the truesize by the amount of headroom added, after orphaning the skb. While here, fix a misleading comment. Thanks to Iouri Kharon for the initial report and testing the fix. Signed-off-by: James Chapman Signed-off-by: David S. Miller diff --git a/drivers/net/pppol2tp.c b/drivers/net/pppol2tp.c index 79359919..8db342f 100644 --- a/drivers/net/pppol2tp.c +++ b/drivers/net/pppol2tp.c @@ -980,6 +980,8 @@ static int pppol2tp_xmit(struct ppp_channel *chan, struct sk_buff *skb) __wsum csum = 0; struct udphdr *uh; unsigned int len; + int old_headroom; + int new_headroom; if (sock_flag(sk, SOCK_DEAD) || !(sk->sk_state & PPPOX_CONNECTED)) goto abort; @@ -1001,16 +1003,18 @@ static int pppol2tp_xmit(struct ppp_channel *chan, struct sk_buff *skb) /* Check that there's enough headroom in the skb to insert IP, * UDP and L2TP and PPP headers. If not enough, expand it to - * make room. Note that a new skb (or a clone) is - * allocated. If we return an error from this point on, make - * sure we free the new skb but do not free the original skb - * since that is done by the caller for the error case. + * make room. Adjust truesize. */ headroom = NET_SKB_PAD + sizeof(struct iphdr) + sizeof(struct udphdr) + hdr_len + sizeof(ppph); + old_headroom = skb_headroom(skb); if (skb_cow_head(skb, headroom)) goto abort; + new_headroom = skb_headroom(skb); + skb_orphan(skb); + skb->truesize += new_headroom - old_headroom; + /* Setup PPP header */ __skb_push(skb, sizeof(ppph)); skb->data[0] = ppph[0]; @@ -1065,7 +1069,6 @@ static int pppol2tp_xmit(struct ppp_channel *chan, struct sk_buff *skb) /* Get routing info from the tunnel socket */ dst_release(skb->dst); skb->dst = dst_clone(__sk_dst_get(sk_tun)); - skb_orphan(skb); skb->sk = sk_tun; /* Queue the packet to IP for output */ -- cgit v0.10.2 From e6da97e7df385a1674cf9f72c31b7a0e46e2620d Mon Sep 17 00:00:00 2001 From: "Robert P. J. Day" Date: Mon, 19 May 2008 14:13:11 -0700 Subject: ipv6: Move from header-y to unifdef-y. Given that contains a __KERNEL__ test, it should be unifdef-ed. Signed-off-by: Robert P. J. Day Signed-off-by: David S. Miller diff --git a/include/linux/Kbuild b/include/linux/Kbuild index b7d81b2..54a4cfb 100644 --- a/include/linux/Kbuild +++ b/include/linux/Kbuild @@ -92,7 +92,6 @@ header-y += if_slip.h header-y += if_strip.h header-y += if_tun.h header-y += if_tunnel.h -header-y += in6.h header-y += in_route.h header-y += ioctl.h header-y += ip6_tunnel.h @@ -236,6 +235,7 @@ unifdef-y += if_vlan.h unifdef-y += igmp.h unifdef-y += inet_diag.h unifdef-y += in.h +unifdef-y += in6.h unifdef-y += inotify.h unifdef-y += input.h unifdef-y += ip.h -- cgit v0.10.2 From 0686caa35ed17cf5b9043f453957e702a7eb588d Mon Sep 17 00:00:00 2001 From: YOSHIFUJI Hideaki Date: Mon, 19 May 2008 16:25:42 -0700 Subject: ndisc: Add missing strategies for per-device retrans timer/reachable time settings. Noticed from Al Viro via David Miller . Signed-off-by: YOSHIFUJI Hideaki Signed-off-by: David S. Miller diff --git a/include/net/ndisc.h b/include/net/ndisc.h index 9c451ff..a01b7c4 100644 --- a/include/net/ndisc.h +++ b/include/net/ndisc.h @@ -129,6 +129,10 @@ extern int ndisc_ifinfo_sysctl_change(struct ctl_table *ctl, void __user *buffer, size_t *lenp, loff_t *ppos); +int ndisc_ifinfo_sysctl_strategy(ctl_table *ctl, int __user *name, + int nlen, void __user *oldval, + size_t __user *oldlenp, + void __user *newval, size_t newlen); #endif extern void inet6_ifinfo_notify(int event, diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c index e591e09..8dd9155 100644 --- a/net/ipv6/addrconf.c +++ b/net/ipv6/addrconf.c @@ -4242,7 +4242,7 @@ static void addrconf_sysctl_register(struct inet6_dev *idev) neigh_sysctl_register(idev->dev, idev->nd_parms, NET_IPV6, NET_IPV6_NEIGH, "ipv6", &ndisc_ifinfo_sysctl_change, - NULL); + ndisc_ifinfo_sysctl_strategy); __addrconf_sysctl_register(dev_net(idev->dev), idev->dev->name, idev->dev->ifindex, idev, &idev->cnf); } diff --git a/net/ipv6/ndisc.c b/net/ipv6/ndisc.c index a55fc05..282fdb3 100644 --- a/net/ipv6/ndisc.c +++ b/net/ipv6/ndisc.c @@ -1727,10 +1727,10 @@ int ndisc_ifinfo_sysctl_change(struct ctl_table *ctl, int write, struct file * f return ret; } -static int ndisc_ifinfo_sysctl_strategy(ctl_table *ctl, int __user *name, - int nlen, void __user *oldval, - size_t __user *oldlenp, - void __user *newval, size_t newlen) +int ndisc_ifinfo_sysctl_strategy(ctl_table *ctl, int __user *name, + int nlen, void __user *oldval, + size_t __user *oldlenp, + void __user *newval, size_t newlen) { struct net_device *dev = ctl->extra1; struct inet6_dev *idev; -- cgit v0.10.2 From a3264435b4ca1ccee54cbef2970f2ba4bef39e2d Mon Sep 17 00:00:00 2001 From: YOSHIFUJI Hideaki Date: Mon, 19 May 2008 16:54:29 -0700 Subject: ipv6 addrconf: Fix route lifetime setting in corner case. Because of arithmetic overflow avoidance, the actual lifetime setting (vs the value given by RA) did not increase monotonically around 0x7fffffff/HZ. Signed-off-by: YOSHIFUJI Hideaki Signed-off-by: David S. Miller diff --git a/net/ipv6/route.c b/net/ipv6/route.c index 12bba08..98aa50c 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c @@ -475,7 +475,7 @@ int rt6_route_rcv(struct net_device *dev, u8 *opt, int len, lifetime = ntohl(rinfo->lifetime); if (lifetime == 0xffffffff) { /* infinity */ - } else if (lifetime > 0x7fffffff/HZ) { + } else if (lifetime > 0x7fffffff/HZ - 1) { /* Avoid arithmetic overflow */ lifetime = 0x7fffffff/HZ - 1; } -- cgit v0.10.2 From 69cdf8f92a8dd191eee0e834c631d84a140b1121 Mon Sep 17 00:00:00 2001 From: YOSHIFUJI Hideaki Date: Mon, 19 May 2008 16:55:13 -0700 Subject: ipv6 route: Fix lifetime in netlink. We could not see appropriate lifetime if the route had been scheduled to expired at 0 (in jiffies). We should check rt6i_flags instead of rt6i_expires to determine whether lifetime is valid or not. Signed-off-by: YOSHIFUJI Hideaki Signed-off-by: David S. Miller diff --git a/net/ipv6/route.c b/net/ipv6/route.c index 98aa50c..b45a7c0 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c @@ -2200,7 +2200,9 @@ static int rt6_fill_node(struct sk_buff *skb, struct rt6_info *rt, NLA_PUT_U32(skb, RTA_PRIORITY, rt->rt6i_metric); - expires = rt->rt6i_expires ? rt->rt6i_expires - jiffies : 0; + expires = (rt->rt6i_flags & RTF_EXPIRES) ? + rt->rt6i_expires - jiffies : 0; + if (rtnl_put_cacheinfo(skb, &rt->u.dst, 0, 0, 0, expires, rt->u.dst.error) < 0) goto nla_put_failure; -- cgit v0.10.2 From 6f704992d3658aadff9e506c7fd80957fce33c5f Mon Sep 17 00:00:00 2001 From: YOSHIFUJI Hideaki Date: Mon, 19 May 2008 16:56:11 -0700 Subject: ipv6 addrconf: Allow infinite prefix lifetime. We need to handle infinite prefix lifetime specially. With help from original reporter "Bonitch, Joseph" . Signed-off-by: YOSHIFUJI Hideaki Signed-off-by: David S. Miller diff --git a/net/ipv6/addrconf.c b/net/ipv6/addrconf.c index 8dd9155..3a83557 100644 --- a/net/ipv6/addrconf.c +++ b/net/ipv6/addrconf.c @@ -1764,14 +1764,16 @@ void addrconf_prefix_rcv(struct net_device *dev, u8 *opt, int len) * 2) Configure prefixes with the auto flag set */ - /* Avoid arithmetic overflow. Really, we could - save rt_expires in seconds, likely valid_lft, - but it would require division in fib gc, that it - not good. - */ - if (valid_lft >= 0x7FFFFFFF/HZ) + if (valid_lft == INFINITY_LIFE_TIME) + rt_expires = ~0UL; + else if (valid_lft >= 0x7FFFFFFF/HZ) { + /* Avoid arithmetic overflow. Really, we could + * save rt_expires in seconds, likely valid_lft, + * but it would require division in fib gc, that it + * not good. + */ rt_expires = 0x7FFFFFFF - (0x7FFFFFFF % HZ); - else + } else rt_expires = valid_lft * HZ; /* @@ -1779,7 +1781,7 @@ void addrconf_prefix_rcv(struct net_device *dev, u8 *opt, int len) * Avoid arithmetic overflow there as well. * Overflow can happen only if HZ < USER_HZ. */ - if (HZ < USER_HZ && rt_expires > 0x7FFFFFFF / USER_HZ) + if (HZ < USER_HZ && ~rt_expires && rt_expires > 0x7FFFFFFF / USER_HZ) rt_expires = 0x7FFFFFFF / USER_HZ; if (pinfo->onlink) { @@ -1788,17 +1790,28 @@ void addrconf_prefix_rcv(struct net_device *dev, u8 *opt, int len) dev->ifindex, 1); if (rt && ((rt->rt6i_flags & (RTF_GATEWAY | RTF_DEFAULT)) == 0)) { - if (rt->rt6i_flags&RTF_EXPIRES) { - if (valid_lft == 0) { - ip6_del_rt(rt); - rt = NULL; - } else { - rt->rt6i_expires = jiffies + rt_expires; - } + /* Autoconf prefix route */ + if (valid_lft == 0) { + ip6_del_rt(rt); + rt = NULL; + } else if (~rt_expires) { + /* not infinity */ + rt->rt6i_expires = jiffies + rt_expires; + rt->rt6i_flags |= RTF_EXPIRES; + } else { + rt->rt6i_flags &= ~RTF_EXPIRES; + rt->rt6i_expires = 0; } } else if (valid_lft) { + int flags = RTF_ADDRCONF | RTF_PREFIX_RT; + clock_t expires = 0; + if (~rt_expires) { + /* not infinity */ + flags |= RTF_EXPIRES; + expires = jiffies_to_clock_t(rt_expires); + } addrconf_prefix_route(&pinfo->prefix, pinfo->prefix_len, - dev, jiffies_to_clock_t(rt_expires), RTF_ADDRCONF|RTF_EXPIRES|RTF_PREFIX_RT); + dev, expires, flags); } if (rt) dst_release(&rt->u.dst); @@ -2021,7 +2034,8 @@ static int inet6_addr_add(struct net *net, int ifindex, struct in6_addr *pfx, struct inet6_dev *idev; struct net_device *dev; int scope; - u32 flags = RTF_EXPIRES; + u32 flags; + clock_t expires; ASSERT_RTNL(); @@ -2041,8 +2055,13 @@ static int inet6_addr_add(struct net *net, int ifindex, struct in6_addr *pfx, if (valid_lft == INFINITY_LIFE_TIME) { ifa_flags |= IFA_F_PERMANENT; flags = 0; - } else if (valid_lft >= 0x7FFFFFFF/HZ) - valid_lft = 0x7FFFFFFF/HZ; + expires = 0; + } else { + if (valid_lft >= 0x7FFFFFFF/HZ) + valid_lft = 0x7FFFFFFF/HZ; + flags = RTF_EXPIRES; + expires = jiffies_to_clock_t(valid_lft * HZ); + } if (prefered_lft == 0) ifa_flags |= IFA_F_DEPRECATED; @@ -2060,7 +2079,7 @@ static int inet6_addr_add(struct net *net, int ifindex, struct in6_addr *pfx, spin_unlock_bh(&ifp->lock); addrconf_prefix_route(&ifp->addr, ifp->prefix_len, dev, - jiffies_to_clock_t(valid_lft * HZ), flags); + expires, flags); /* * Note that section 3.1 of RFC 4429 indicates * that the Optimistic flag should not be set for @@ -3148,7 +3167,8 @@ inet6_rtm_deladdr(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg) static int inet6_addr_modify(struct inet6_ifaddr *ifp, u8 ifa_flags, u32 prefered_lft, u32 valid_lft) { - u32 flags = RTF_EXPIRES; + u32 flags; + clock_t expires; if (!valid_lft || (prefered_lft > valid_lft)) return -EINVAL; @@ -3156,8 +3176,13 @@ static int inet6_addr_modify(struct inet6_ifaddr *ifp, u8 ifa_flags, if (valid_lft == INFINITY_LIFE_TIME) { ifa_flags |= IFA_F_PERMANENT; flags = 0; - } else if (valid_lft >= 0x7FFFFFFF/HZ) - valid_lft = 0x7FFFFFFF/HZ; + expires = 0; + } else { + if (valid_lft >= 0x7FFFFFFF/HZ) + valid_lft = 0x7FFFFFFF/HZ; + flags = RTF_EXPIRES; + expires = jiffies_to_clock_t(valid_lft * HZ); + } if (prefered_lft == 0) ifa_flags |= IFA_F_DEPRECATED; @@ -3176,7 +3201,7 @@ static int inet6_addr_modify(struct inet6_ifaddr *ifp, u8 ifa_flags, ipv6_ifa_notify(0, ifp); addrconf_prefix_route(&ifp->addr, ifp->prefix_len, ifp->idev->dev, - jiffies_to_clock_t(valid_lft * HZ), flags); + expires, flags); addrconf_verify(0); return 0; diff --git a/net/ipv6/route.c b/net/ipv6/route.c index b45a7c0..b7a4a87 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c @@ -1106,7 +1106,9 @@ int ip6_route_add(struct fib6_config *cfg) } rt->u.dst.obsolete = -1; - rt->rt6i_expires = jiffies + clock_t_to_jiffies(cfg->fc_expires); + rt->rt6i_expires = (cfg->fc_flags & RTF_EXPIRES) ? + jiffies + clock_t_to_jiffies(cfg->fc_expires) : + 0; if (cfg->fc_protocol == RTPROT_UNSPEC) cfg->fc_protocol = RTPROT_BOOT; -- cgit v0.10.2 From 1ac06e0306d0192a7a4d9ea1c9e06d355ce7e7d3 Mon Sep 17 00:00:00 2001 From: Herbert Xu Date: Tue, 20 May 2008 14:32:14 -0700 Subject: ipsec: Use the correct ip_local_out function Because the IPsec output function xfrm_output_resume does its own dst_output call it should always call __ip_local_output instead of ip_local_output as the latter may invoke dst_output directly. Otherwise the return values from nf_hook and dst_output may clash as they both use the value 1 but for different purposes. When that clash occurs this can cause a packet to be used after it has been freed which usually leads to a crash. Because the offending value is only returned from dst_output with qdiscs such as HTB, this bug is normally not visible. Thanks to Marco Berizzi for his perseverance in tracking this down. Signed-off-by: Herbert Xu Signed-off-by: David S. Miller diff --git a/net/ipv4/route.c b/net/ipv4/route.c index 92f90ae..df41026 100644 --- a/net/ipv4/route.c +++ b/net/ipv4/route.c @@ -160,7 +160,7 @@ static struct dst_ops ipv4_dst_ops = { .negative_advice = ipv4_negative_advice, .link_failure = ipv4_link_failure, .update_pmtu = ip_rt_update_pmtu, - .local_out = ip_local_out, + .local_out = __ip_local_out, .entry_size = sizeof(struct rtable), .entries = ATOMIC_INIT(0), }; diff --git a/net/ipv6/route.c b/net/ipv6/route.c index b7a4a87..48534c6 100644 --- a/net/ipv6/route.c +++ b/net/ipv6/route.c @@ -109,7 +109,7 @@ static struct dst_ops ip6_dst_ops_template = { .negative_advice = ip6_negative_advice, .link_failure = ip6_link_failure, .update_pmtu = ip6_rt_update_pmtu, - .local_out = ip6_local_out, + .local_out = __ip6_local_out, .entry_size = sizeof(struct rt6_info), .entries = ATOMIC_INIT(0), }; -- cgit v0.10.2 From f2df824948d559ea818e03486a8583e42ea6ab37 Mon Sep 17 00:00:00 2001 From: Patrick McHardy Date: Tue, 20 May 2008 14:34:46 -0700 Subject: net_sched: cls_api: fix return value for non-existant classifiers cls_api should return ENOENT when the requested classifier doesn't exist. Signed-off-by: Patrick McHardy Signed-off-by: David S. Miller diff --git a/net/sched/cls_api.c b/net/sched/cls_api.c index 1086df7..9360fc8 100644 --- a/net/sched/cls_api.c +++ b/net/sched/cls_api.c @@ -220,7 +220,7 @@ replay: tp = kzalloc(sizeof(*tp), GFP_KERNEL); if (tp == NULL) goto errout; - err = -EINVAL; + err = -ENOENT; tp_ops = tcf_proto_lookup_ops(tca[TCA_KIND]); if (tp_ops == NULL) { #ifdef CONFIG_KMOD -- cgit v0.10.2 From 0e91796eb46e29edc791131c832a2232bcaed9dd Mon Sep 17 00:00:00 2001 From: David Woodhouse Date: Tue, 20 May 2008 14:36:14 -0700 Subject: net: Fix call to ->change_rx_flags(dev, IFF_MULTICAST) in dev_change_flags() Am I just being particularly dim today, or can the call to dev->change_rx_flags(dev, IFF_MULTICAST) in dev_change_flags() never happen? We've just set dev->flags = flags & IFF_MULTICAST, effectively. So the condition '(dev->flags ^ flags) & IFF_MULTICAST' is _never_ going to be true. Signed-off-by: David Woodhouse Signed-off-by: David S. Miller diff --git a/net/core/dev.c b/net/core/dev.c index ce88c0d..5829630 100644 --- a/net/core/dev.c +++ b/net/core/dev.c @@ -3141,7 +3141,7 @@ int dev_change_flags(struct net_device *dev, unsigned flags) * Load in the correct multicast list now the flags have changed. */ - if (dev->change_rx_flags && (dev->flags ^ flags) & IFF_MULTICAST) + if (dev->change_rx_flags && (old_flags ^ flags) & IFF_MULTICAST) dev->change_rx_flags(dev, IFF_MULTICAST); dev_set_rx_mode(dev); -- cgit v0.10.2 From 81d85346b3fcd8b3167eac8b5fb415a210bd4345 Mon Sep 17 00:00:00 2001 From: Patrick McHardy Date: Tue, 20 May 2008 14:37:36 -0700 Subject: vlan: Correctly handle device notifications for layered VLAN devices Commit 30688a9 ([VLAN]: Handle vlan devices net namespace changing) changed the device notifier to special-case notifications for VLAN devices, effectively disabling state propagation to underlying VLAN devices. This is needed for layered VLANs though, so restore the original behaviour. Signed-off-by: Patrick McHardy Acked-by: Pavel Emelyanov Signed-off-by: David S. Miller diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c index 2a739ad..b934159 100644 --- a/net/8021q/vlan.c +++ b/net/8021q/vlan.c @@ -410,10 +410,8 @@ static int vlan_device_event(struct notifier_block *unused, unsigned long event, int i, flgs; struct net_device *vlandev; - if (is_vlan_dev(dev)) { + if (is_vlan_dev(dev)) __vlan_device_event(dev, event); - goto out; - } grp = __vlan_find_group(dev); if (!grp) -- cgit v0.10.2 From 7ff6e6f779960e1078a78b60a881571c04f52b9b Mon Sep 17 00:00:00 2001 From: Adrian Bunk Date: Tue, 20 May 2008 14:52:25 -0700 Subject: drivers/atm/: remove CVS keywords This patch removes CVS keywords that weren't updated for a long time. Signed-off-by: Adrian Bunk Acked-by: Chas Williams Signed-off-by: David S. Miller diff --git a/drivers/atm/fore200e.h b/drivers/atm/fore200e.h index 183841c..8dd4aa7 100644 --- a/drivers/atm/fore200e.h +++ b/drivers/atm/fore200e.h @@ -1,4 +1,3 @@ -/* $Id: fore200e.h,v 1.4 2000/04/14 10:10:34 davem Exp $ */ #ifndef _FORE200E_H #define _FORE200E_H diff --git a/drivers/atm/fore200e_mkfirm.c b/drivers/atm/fore200e_mkfirm.c index 2ebe1a1..520e14b 100644 --- a/drivers/atm/fore200e_mkfirm.c +++ b/drivers/atm/fore200e_mkfirm.c @@ -1,6 +1,4 @@ /* - $Id: fore200e_mkfirm.c,v 1.1 2000/02/21 16:04:32 davem Exp $ - mkfirm.c: generates a C readable file from a binary firmware image Christophe Lizzi (lizzi@{csti.fr, cnam.fr}), June 1999. diff --git a/drivers/atm/he.h b/drivers/atm/he.h index 1dc2775..fe6cd15a 100644 --- a/drivers/atm/he.h +++ b/drivers/atm/he.h @@ -1,5 +1,3 @@ -/* $Id: he.h,v 1.4 2003/05/06 22:48:00 chas Exp $ */ - /* he.h diff --git a/drivers/atm/idt77252.c b/drivers/atm/idt77252.c index 28d77b5..3a504e9 100644 --- a/drivers/atm/idt77252.c +++ b/drivers/atm/idt77252.c @@ -1,8 +1,4 @@ /******************************************************************* - * ident "$Id: idt77252.c,v 1.2 2001/11/11 08:13:54 ecd Exp $" - * - * $Author: ecd $ - * $Date: 2001/11/11 08:13:54 $ * * Copyright (c) 2000 ATecoM GmbH * @@ -29,9 +25,6 @@ * 675 Mass Ave, Cambridge, MA 02139, USA. * *******************************************************************/ -static char const rcsid[] = -"$Id: idt77252.c,v 1.2 2001/11/11 08:13:54 ecd Exp $"; - #include #include diff --git a/drivers/atm/idt77252.h b/drivers/atm/idt77252.h index 6f2b4a5..e83eaf1 100644 --- a/drivers/atm/idt77252.h +++ b/drivers/atm/idt77252.h @@ -1,8 +1,4 @@ /******************************************************************* - * ident "$Id: idt77252.h,v 1.2 2001/11/11 08:13:54 ecd Exp $" - * - * $Author: ecd $ - * $Date: 2001/11/11 08:13:54 $ * * Copyright (c) 2000 ATecoM GmbH * diff --git a/drivers/atm/nicstarmac.copyright b/drivers/atm/nicstarmac.copyright index 2e15b39..180531a 100644 --- a/drivers/atm/nicstarmac.copyright +++ b/drivers/atm/nicstarmac.copyright @@ -13,7 +13,7 @@ * * Modified to work with the IDT7721 nicstar -- AAL5 (tested) only. * - * R. D. Rechenmacher , Aug. 6, 1997 $Revision: 1.1 $ $Date: 1999/08/20 11:00:11 $ + * R. D. Rechenmacher , Aug. 6, 1997 * * Linux driver for the IDT77201 NICStAR PCI ATM controller. * PHY component is expected to be 155 Mbps S/UNI-Lite or IDT 77155; -- cgit v0.10.2 From 5fb13570543f4ae022996c9d7c0c099c8abf22dd Mon Sep 17 00:00:00 2001 From: Patrick McHardy Date: Tue, 20 May 2008 14:54:50 -0700 Subject: [VLAN]: Propagate selected feature bits to VLAN devices Propagate feature bits from the NETDEV_FEAT_CHANGE notifier. For now only TSO is propagated for devices that announce their ability to support TSO in combination with VLAN accel by setting the NETIF_F_VLAN_TSO flag. Signed-off-by: Patrick McHardy Signed-off-by: David S. Miller diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h index b11e6e1..2b02664 100644 --- a/include/linux/netdevice.h +++ b/include/linux/netdevice.h @@ -514,10 +514,12 @@ struct net_device #define NETIF_F_NETNS_LOCAL 8192 /* Does not change network namespaces */ #define NETIF_F_MULTI_QUEUE 16384 /* Has multiple TX/RX queues */ #define NETIF_F_LRO 32768 /* large receive offload */ +#define NETIF_F_VLAN_TSO 65536 /* Supports TSO for VLANs */ +#define NETIF_F_VLAN_CSUM 131072 /* Supports TX checksumming for VLANs */ /* Segmentation offload features */ -#define NETIF_F_GSO_SHIFT 16 -#define NETIF_F_GSO_MASK 0xffff0000 +#define NETIF_F_GSO_SHIFT 20 +#define NETIF_F_GSO_MASK 0xfff00000 #define NETIF_F_TSO (SKB_GSO_TCPV4 << NETIF_F_GSO_SHIFT) #define NETIF_F_UFO (SKB_GSO_UDP << NETIF_F_GSO_SHIFT) #define NETIF_F_GSO_ROBUST (SKB_GSO_DODGY << NETIF_F_GSO_SHIFT) diff --git a/net/8021q/vlan.c b/net/8021q/vlan.c index b934159..5196130 100644 --- a/net/8021q/vlan.c +++ b/net/8021q/vlan.c @@ -382,6 +382,24 @@ static void vlan_sync_address(struct net_device *dev, memcpy(vlan->real_dev_addr, dev->dev_addr, ETH_ALEN); } +static void vlan_transfer_features(struct net_device *dev, + struct net_device *vlandev) +{ + unsigned long old_features = vlandev->features; + + if (dev->features & NETIF_F_VLAN_TSO) { + vlandev->features &= ~VLAN_TSO_FEATURES; + vlandev->features |= dev->features & VLAN_TSO_FEATURES; + } + if (dev->features & NETIF_F_VLAN_CSUM) { + vlandev->features &= ~NETIF_F_ALL_CSUM; + vlandev->features |= dev->features & NETIF_F_ALL_CSUM; + } + + if (old_features != vlandev->features) + netdev_features_change(vlandev); +} + static void __vlan_device_event(struct net_device *dev, unsigned long event) { switch (event) { @@ -448,6 +466,18 @@ static int vlan_device_event(struct notifier_block *unused, unsigned long event, } break; + case NETDEV_FEAT_CHANGE: + /* Propagate device features to underlying device */ + for (i = 0; i < VLAN_GROUP_ARRAY_LEN; i++) { + vlandev = vlan_group_get_device(grp, i); + if (!vlandev) + continue; + + vlan_transfer_features(dev, vlandev); + } + + break; + case NETDEV_DOWN: /* Put all VLANs for this dev in the down state too. */ for (i = 0; i < VLAN_GROUP_ARRAY_LEN; i++) { diff --git a/net/8021q/vlan.h b/net/8021q/vlan.h index 5229a72..7962569 100644 --- a/net/8021q/vlan.h +++ b/net/8021q/vlan.h @@ -7,6 +7,8 @@ #define VLAN_GRP_HASH_SIZE (1 << VLAN_GRP_HASH_SHIFT) #define VLAN_GRP_HASH_MASK (VLAN_GRP_HASH_SIZE - 1) +#define VLAN_TSO_FEATURES (NETIF_F_TSO | NETIF_F_TSO6 | NETIF_F_SG) + /* Find a VLAN device by the MAC address of its Ethernet device, and * it's VLAN ID. The default configuration is to have VLAN's scope * to be box-wide, so the MAC will be ignored. The mac will only be diff --git a/net/8021q/vlan_dev.c b/net/8021q/vlan_dev.c index c961f08..b1cfbaa 100644 --- a/net/8021q/vlan_dev.c +++ b/net/8021q/vlan_dev.c @@ -663,6 +663,11 @@ static int vlan_dev_init(struct net_device *dev) (1<<__LINK_STATE_DORMANT))) | (1<<__LINK_STATE_PRESENT); + if (real_dev->features & NETIF_F_VLAN_TSO) + dev->features |= real_dev->features & VLAN_TSO_FEATURES; + if (real_dev->features & NETIF_F_VLAN_CSUM) + dev->features |= real_dev->features & NETIF_F_ALL_CSUM; + /* ipv6 shared card related stuff */ dev->dev_id = real_dev->dev_id; -- cgit v0.10.2 From d3ede327e83f202c3a0962e207318f65717c5eb7 Mon Sep 17 00:00:00 2001 From: "Denis V. Lunev" Date: Tue, 20 May 2008 15:12:44 -0700 Subject: pktgen: make sure that pktgen_thread_worker has been executed The following courruption can happen during pktgen stop: list_del corruption. prev->next should be ffff81007e8a5e70, but was 6b6b6b6b6b6b6b6b kernel BUG at lib/list_debug.c:67! :pktgen:pktgen_thread_worker+0x374/0x10b0 ? autoremove_wake_function+0x0/0x40 ? _spin_unlock_irqrestore+0x42/0x80 ? :pktgen:pktgen_thread_worker+0x0/0x10b0 kthread+0x4d/0x80 child_rip+0xa/0x12 ? restore_args+0x0/0x30 ? kthread+0x0/0x80 ? child_rip+0x0/0x12 RIP list_del+0x48/0x70 The problem is that pktgen_thread_worker can not be executed if kthread_stop has been called too early. Insert a completion on the normal initialization path to make sure that pktgen_thread_worker will gain the control for sure. Signed-off-by: Denis V. Lunev Acked-by: Alexey Dobriyan Signed-off-by: David S. Miller diff --git a/net/core/pktgen.c b/net/core/pktgen.c index 8dca211..fdf5377 100644 --- a/net/core/pktgen.c +++ b/net/core/pktgen.c @@ -390,6 +390,7 @@ struct pktgen_thread { int cpu; wait_queue_head_t queue; + struct completion start_done; }; #define REMOVE 1 @@ -3414,6 +3415,7 @@ static int pktgen_thread_worker(void *arg) BUG_ON(smp_processor_id() != cpu); init_waitqueue_head(&t->queue); + complete(&t->start_done); pr_debug("pktgen: starting pktgen/%d: pid=%d\n", cpu, task_pid_nr(current)); @@ -3615,6 +3617,7 @@ static int __init pktgen_create_thread(int cpu) INIT_LIST_HEAD(&t->if_list); list_add_tail(&t->th_list, &pktgen_threads); + init_completion(&t->start_done); p = kthread_create(pktgen_thread_worker, t, "kpktgend_%d", cpu); if (IS_ERR(p)) { @@ -3639,6 +3642,7 @@ static int __init pktgen_create_thread(int cpu) } wake_up_process(p); + wait_for_completion(&t->start_done); return 0; } -- cgit v0.10.2