* Re: 2.6.23-rc2-mm2
From: Eric W. Biederman @ 2007-08-10 21:19 UTC (permalink / raw)
To: Andrew Morton
Cc: Gabriel C, Michal Piotrowski, linux-kernel, Netdev, coreteam
In-Reply-To: <20070810124156.2de9710e.akpm@linux-foundation.org>
Andrew Morton <akpm@linux-foundation.org> writes:
> There seems to be rather a lot of damage here.
>
> I assume that the sysctl changes are what caused the netfilter oopses.
>
> - nf_conntrack_init() calls nf_conntrack_expect_init() which fails due to
> sysctl problems.
In particular sysctl_check_table finds issues with the sysctl table
so register_sysctl_table refuses to register it.
> - nf_conntrack_init() bales out without calling nf_conntrack_helper_init()
>
> So nf_ct_helper_hsize never gets initialised.
>
> - Later, netfilter client code calls helper_hash(), which gets a
> divide-by-zero due to nf_ct_helper_hsize==0.
>
>
> yeah, that's a netfilter bug, but we're trying to get kernels tested here.
> If I'm feeling energetic I'll drop the sysctl changes and do rc2-mm3.
> Probably I won't feel energetic, but we'll need a lot of fixes here before
> I can release the sysctl changes in another -mm, please.
As a cheap workaround it should be possible to disable SYSCTL support
in 2.6.23-rc2-mm2 to get around these issues.
Andrew for the moment I have just sent you fixes for all of the issues
that I am aware of. Mostly they are cheap kill the sys_sysctl()
support patches.
Hopefully that is enough to bring the pain level down to manageable.
I hadn't anticipated subsystems failing because they could not register
their sysctl tables. I was simply expecting things not to show up in
/proc/sys. And more of the pain of making working sysctl tables to
be pushed back to developers.
Eric
^ permalink raw reply
* RE: [PATCH 9/24] make atomic_read() behave consistently on ia64
From: Luck, Tony @ 2007-08-10 21:19 UTC (permalink / raw)
To: Chris Snook
Cc: linux-kernel, linux-arch, torvalds, netdev, akpm, ak,
heiko.carstens, davem, schwidefsky, wensong, horms, wjiang,
cfriesen, zlynx, rpjday, jesper.juhl
In-Reply-To: <46BCC1AF.5050204@redhat.com>
> That's distressing. I'm about to resubmit with a volatile cast in
> atomic_set as well, since people expect that behavior and I've been
> shown a legitimate case where it could matter. Does the assembly look
> right with that cast in atomic_set() as well?
No. With the casts to volatile in atomic_set and atomic64_set I
still see places where ld8 is changed to ld4 + sign-extend.
-Tony
^ permalink raw reply
* [patch 09/18] Clean up duplicate includes in drivers/net/
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, jesper.juhl, linville
From: Jesper Juhl <jesper.juhl@gmail.com>
This patch cleans up duplicate includes in
drivers/net/
Signed-off-by: Jesper Juhl <jesper.juhl@gmail.com>
Acked-by: "John W. Linville" <linville@tuxdriver.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/atl1/atl1_main.c | 1 -
drivers/net/bfin_mac.c | 5 -----
drivers/net/bonding/bond_sysfs.c | 1 -
drivers/net/fs_enet/fs_enet-main.c | 2 --
drivers/net/gianfar.h | 1 -
drivers/net/gianfar_ethtool.c | 1 -
drivers/net/irda/kingsun-sir.c | 1 -
drivers/net/irda/mcs7780.c | 1 -
drivers/net/mipsnet.c | 1 -
drivers/net/netxen/netxen_nic_main.c | 1 -
drivers/net/qla3xxx.c | 1 -
drivers/net/tsi108_eth.c | 1 -
drivers/net/wireless/ipw2200.h | 1 -
drivers/net/wireless/zd1211rw/zd_def.h | 1 -
14 files changed, 19 deletions(-)
diff -puN drivers/net/atl1/atl1_main.c~clean-up-duplicate-includes-in-drivers-net drivers/net/atl1/atl1_main.c
--- a/drivers/net/atl1/atl1_main.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/atl1/atl1_main.c
@@ -76,7 +76,6 @@
#include <linux/compiler.h>
#include <linux/delay.h>
#include <linux/mii.h>
-#include <linux/interrupt.h>
#include <net/checksum.h>
#include <asm/atomic.h>
diff -puN drivers/net/bfin_mac.c~clean-up-duplicate-includes-in-drivers-net drivers/net/bfin_mac.c
--- a/drivers/net/bfin_mac.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/bfin_mac.c
@@ -47,15 +47,10 @@
#include <linux/spinlock.h>
#include <linux/ethtool.h>
#include <linux/mii.h>
-
#include <linux/netdevice.h>
#include <linux/etherdevice.h>
#include <linux/skbuff.h>
-
#include <linux/platform_device.h>
-#include <linux/netdevice.h>
-#include <linux/etherdevice.h>
-#include <linux/skbuff.h>
#include <asm/dma.h>
#include <linux/dma-mapping.h>
diff -puN drivers/net/bonding/bond_sysfs.c~clean-up-duplicate-includes-in-drivers-net drivers/net/bonding/bond_sysfs.c
--- a/drivers/net/bonding/bond_sysfs.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/bonding/bond_sysfs.c
@@ -31,7 +31,6 @@
#include <linux/inetdevice.h>
#include <linux/in.h>
#include <linux/sysfs.h>
-#include <linux/string.h>
#include <linux/ctype.h>
#include <linux/inet.h>
#include <linux/rtnetlink.h>
diff -puN drivers/net/fs_enet/fs_enet-main.c~clean-up-duplicate-includes-in-drivers-net drivers/net/fs_enet/fs_enet-main.c
--- a/drivers/net/fs_enet/fs_enet-main.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/fs_enet/fs_enet-main.c
@@ -39,8 +39,6 @@
#include <linux/vmalloc.h>
#include <asm/pgtable.h>
-
-#include <asm/pgtable.h>
#include <asm/irq.h>
#include <asm/uaccess.h>
diff -puN drivers/net/gianfar.h~clean-up-duplicate-includes-in-drivers-net drivers/net/gianfar.h
--- a/drivers/net/gianfar.h~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/gianfar.h
@@ -45,7 +45,6 @@
#include <linux/crc32.h>
#include <linux/workqueue.h>
#include <linux/ethtool.h>
-#include <linux/netdevice.h>
#include <linux/fsl_devices.h>
#include "gianfar_mii.h"
diff -puN drivers/net/gianfar_ethtool.c~clean-up-duplicate-includes-in-drivers-net drivers/net/gianfar_ethtool.c
--- a/drivers/net/gianfar_ethtool.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/gianfar_ethtool.c
@@ -34,7 +34,6 @@
#include <linux/module.h>
#include <linux/crc32.h>
#include <asm/types.h>
-#include <asm/uaccess.h>
#include <linux/ethtool.h>
#include <linux/mii.h>
#include <linux/phy.h>
diff -puN drivers/net/irda/kingsun-sir.c~clean-up-duplicate-includes-in-drivers-net drivers/net/irda/kingsun-sir.c
--- a/drivers/net/irda/kingsun-sir.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/irda/kingsun-sir.c
@@ -66,7 +66,6 @@
#include <linux/errno.h>
#include <linux/init.h>
#include <linux/slab.h>
-#include <linux/module.h>
#include <linux/kref.h>
#include <linux/usb.h>
#include <linux/device.h>
diff -puN drivers/net/irda/mcs7780.c~clean-up-duplicate-includes-in-drivers-net drivers/net/irda/mcs7780.c
--- a/drivers/net/irda/mcs7780.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/irda/mcs7780.c
@@ -50,7 +50,6 @@
#include <linux/errno.h>
#include <linux/init.h>
#include <linux/slab.h>
-#include <linux/module.h>
#include <linux/kref.h>
#include <linux/usb.h>
#include <linux/device.h>
diff -puN drivers/net/mipsnet.c~clean-up-duplicate-includes-in-drivers-net drivers/net/mipsnet.c
--- a/drivers/net/mipsnet.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/mipsnet.c
@@ -11,7 +11,6 @@
#include <linux/module.h>
#include <linux/netdevice.h>
#include <linux/etherdevice.h>
-#include <linux/netdevice.h>
#include <linux/platform_device.h>
#include <asm/io.h>
#include <asm/mips-boards/simint.h>
diff -puN drivers/net/netxen/netxen_nic_main.c~clean-up-duplicate-includes-in-drivers-net drivers/net/netxen/netxen_nic_main.c
--- a/drivers/net/netxen/netxen_nic_main.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/netxen/netxen_nic_main.c
@@ -39,7 +39,6 @@
#include "netxen_nic_phan_reg.h"
#include <linux/dma-mapping.h>
-#include <linux/vmalloc.h>
#include <net/ip.h>
MODULE_DESCRIPTION("NetXen Multi port (1/10) Gigabit Network Driver");
diff -puN drivers/net/qla3xxx.c~clean-up-duplicate-includes-in-drivers-net drivers/net/qla3xxx.c
--- a/drivers/net/qla3xxx.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/qla3xxx.c
@@ -31,7 +31,6 @@
#include <linux/skbuff.h>
#include <linux/rtnetlink.h>
#include <linux/if_vlan.h>
-#include <linux/init.h>
#include <linux/delay.h>
#include <linux/mm.h>
diff -puN drivers/net/tsi108_eth.c~clean-up-duplicate-includes-in-drivers-net drivers/net/tsi108_eth.c
--- a/drivers/net/tsi108_eth.c~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/tsi108_eth.c
@@ -47,7 +47,6 @@
#include <linux/rtnetlink.h>
#include <linux/timer.h>
#include <linux/platform_device.h>
-#include <linux/etherdevice.h>
#include <asm/system.h>
#include <asm/io.h>
diff -puN drivers/net/wireless/ipw2200.h~clean-up-duplicate-includes-in-drivers-net drivers/net/wireless/ipw2200.h
--- a/drivers/net/wireless/ipw2200.h~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/wireless/ipw2200.h
@@ -45,7 +45,6 @@
#include <linux/firmware.h>
#include <linux/wireless.h>
-#include <linux/dma-mapping.h>
#include <linux/jiffies.h>
#include <asm/io.h>
diff -puN drivers/net/wireless/zd1211rw/zd_def.h~clean-up-duplicate-includes-in-drivers-net drivers/net/wireless/zd1211rw/zd_def.h
--- a/drivers/net/wireless/zd1211rw/zd_def.h~clean-up-duplicate-includes-in-drivers-net
+++ a/drivers/net/wireless/zd1211rw/zd_def.h
@@ -21,7 +21,6 @@
#include <linux/kernel.h>
#include <linux/stringify.h>
#include <linux/device.h>
-#include <linux/kernel.h>
typedef u16 __nocast zd_addr_t;
_
^ permalink raw reply
* [patch 26/28] netconsole: Support dynamic reconfiguration using configfs
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, Joel.Becker, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
This patch introduces support for dynamic reconfiguration (adding, removing
and/or modifying parameters of netconsole targets at runtime) using a
userspace interface exported via configfs. Documentation is also updated
accordingly.
Issues and brief design overview:
(1) Kernel-initiated creation / destruction of kernel objects is not
possible with configfs -- the lifetimes of the "config items" is managed
exclusively from userspace. But netconsole must support boot/module
params too, and these are parsed in kernel and hence netpolls must be
setup from the kernel. Joel Becker suggested to separately manage the
lifetimes of the two kinds of netconsole_target objects -- those created
via configfs mkdir(2) from userspace and those specified from the
boot/module option string. This adds complexity and some redundancy here
and also means that boot/module param-created targets are not exposed
through the configfs namespace (and hence cannot be updated / destroyed
dynamically). However, this saves us from locking / refcounting
complexities that would need to be introduced in configfs to support
kernel-initiated item creation / destroy there.
(2) In configfs, item creation takes place in the call chain of the
mkdir(2) syscall in the driver subsystem. If we used an ioctl(2) to
create / destroy objects from userspace, the special userspace program is
able to fill out the structure to be passed into the ioctl and hence
specify attributes such as local interface that are required at the time
we set up the netpoll. For configfs, this information is not available at
the time of mkdir(2). So, we keep all newly-created targets (via
configfs) disabled by default. The user is expected to set various
attributes appropriately (including the local network interface if
required) and then write(2) "1" to the "enabled" attribute. Thus,
netpoll_setup() is then called on the set parameters in the context of
_this_ write(2) on the "enabled" attribute itself. This design enables
the user to reconfigure existing netconsole targets at runtime to be
attached to newly-come-up interfaces that may not have existed when
netconsole was loaded or when the targets were actually created. All this
effectively enables us to get rid of custom ioctls.
(3) Ultra-paranoid configfs attribute show() and store() operations, with
sanity and input range checking, using only safe string primitives, and
compliant with the recommendations in Documentation/filesystems/sysfs.txt.
(4) A new function netpoll_print_options() is created in the netpoll API,
that just prints out the configured parameters for a netpoll structure.
netpoll_parse_options() is modified to use that and it is also exported to
be used from netconsole.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Acked-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Cc: Matt Mackall <mpm@selenic.com>
Cc: Joel Becker <Joel.Becker@oracle.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
Documentation/networking/netconsole.txt | 68 ++
drivers/net/Kconfig | 10
drivers/net/netconsole.c | 605 +++++++++++++++++++++-
include/linux/netpoll.h | 1
net/core/netpoll.c | 44 -
5 files changed, 683 insertions(+), 45 deletions(-)
diff -puN Documentation/networking/netconsole.txt~netconsole-support-dynamic-reconfiguration-using-configfs Documentation/networking/netconsole.txt
--- a/Documentation/networking/netconsole.txt~netconsole-support-dynamic-reconfiguration-using-configfs
+++ a/Documentation/networking/netconsole.txt
@@ -3,6 +3,10 @@ started by Ingo Molnar <mingo@redhat.com
2.6 port and netpoll api by Matt Mackall <mpm@selenic.com>, Sep 9 2003
Please send bug reports to Matt Mackall <mpm@selenic.com>
+and Satyam Sharma <satyam.sharma@gmail.com>
+
+Introduction:
+=============
This module logs kernel printk messages over UDP allowing debugging of
problem where disk logging fails and serial consoles are impractical.
@@ -13,6 +17,9 @@ the specified interface as soon as possi
capture of early kernel panics, it does capture most of the boot
process.
+Sender and receiver configuration:
+==================================
+
It takes a string configuration parameter "netconsole" in the
following format:
@@ -46,6 +53,67 @@ address.
The remote host can run either 'netcat -u -l -p <port>' or syslogd.
+Dynamic reconfiguration:
+========================
+
+Dynamic reconfigurability is a useful addition to netconsole that enables
+remote logging targets to be dynamically added, removed, or have their
+parameters reconfigured at runtime from a configfs-based userspace interface.
+[ Note that the parameters of netconsole targets that were specified/created
+from the boot/module option are not exposed via this interface, and hence
+cannot be modified dynamically. ]
+
+To include this feature, select CONFIG_NETCONSOLE_DYNAMIC when building the
+netconsole module (or kernel, if netconsole is built-in).
+
+Some examples follow (where configfs is mounted at the /sys/kernel/config
+mountpoint).
+
+To add a remote logging target (target names can be arbitrary):
+
+ cd /sys/kernel/config/netconsole/
+ mkdir target1
+
+Note that newly created targets have default parameter values (as mentioned
+above) and are disabled by default -- they must first be enabled by writing
+"1" to the "enabled" attribute (usually after setting parameters accordingly)
+as described below.
+
+To remove a target:
+
+ rmdir /sys/kernel/config/netconsole/othertarget/
+
+The interface exposes these parameters of a netconsole target to userspace:
+
+ enabled Is this target currently enabled? (read-write)
+ dev_name Local network interface name (read-write)
+ local_port Source UDP port to use (read-write)
+ remote_port Remote agent's UDP port (read-write)
+ local_ip Source IP address to use (read-write)
+ remote_ip Remote agent's IP address (read-write)
+ local_mac Local interface's MAC address (read-only)
+ remote_mac Remote agent's MAC address (read-write)
+
+The "enabled" attribute is also used to control whether the parameters of
+a target can be updated or not -- you can modify the parameters of only
+disabled targets (i.e. if "enabled" is 0).
+
+To update a target's parameters:
+
+ cat enabled # check if enabled is 1
+ echo 0 > enabled # disable the target (if required)
+ echo eth2 > dev_name # set local interface
+ echo 10.0.0.4 > remote_ip # update some parameter
+ echo cb:a9:87:65:43:21 > remote_mac # update more parameters
+ echo 1 > enabled # enable target again
+
+You can also update the local interface dynamically. This is especially
+useful if you want to use interfaces that have newly come up (and may not
+have existed when netconsole was loaded / initialized).
+
+Miscellaneous notes:
+====================
+
WARNING: the default target ethernet setting uses the broadcast
ethernet address to send packets, which can cause increased load on
other systems on the same ethernet segment.
diff -puN drivers/net/Kconfig~netconsole-support-dynamic-reconfiguration-using-configfs drivers/net/Kconfig
--- a/drivers/net/Kconfig~netconsole-support-dynamic-reconfiguration-using-configfs
+++ a/drivers/net/Kconfig
@@ -3021,6 +3021,16 @@ config NETCONSOLE
If you want to log kernel messages over the network, enable this.
See <file:Documentation/networking/netconsole.txt> for details.
+config NETCONSOLE_DYNAMIC
+ bool "Dynamic reconfiguration of logging targets (EXPERIMENTAL)"
+ depends on NETCONSOLE && SYSFS && EXPERIMENTAL
+ select CONFIGFS_FS
+ help
+ This option enables the ability to dynamically reconfigure target
+ parameters (interface, IP addresses, port numbers, MAC addresses)
+ at runtime through a userspace interface exported using configfs.
+ See <file:Documentation/networking/netconsole.txt> for details.
+
config NETPOLL
def_bool NETCONSOLE
diff -puN drivers/net/netconsole.c~netconsole-support-dynamic-reconfiguration-using-configfs drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-support-dynamic-reconfiguration-using-configfs
+++ a/drivers/net/netconsole.c
@@ -41,6 +41,8 @@
#include <linux/moduleparam.h>
#include <linux/string.h>
#include <linux/netpoll.h>
+#include <linux/inet.h>
+#include <linux/configfs.h>
MODULE_AUTHOR("Maintainer: Matt Mackall <mpm@selenic.com>");
MODULE_DESCRIPTION("Console driver for network interfaces");
@@ -71,20 +73,100 @@ static DEFINE_SPINLOCK(target_list_lock)
/**
* struct netconsole_target - Represents a configured netconsole target.
* @list: Links this target into the target_list.
+ * @item: Links us into the configfs subsystem hierarchy.
+ * @enabled: On / off knob to enable / disable target.
+ * Visible from userspace (read-write).
+ * We maintain a strict 1:1 correspondence between this and
+ * whether the corresponding netpoll is active or inactive.
+ * Also, other parameters of a target may be modified at
+ * runtime only when it is disabled (enabled == 0).
* @np: The netpoll structure for this target.
+ * Contains the other userspace visible parameters:
+ * dev_name (read-write)
+ * local_port (read-write)
+ * remote_port (read-write)
+ * local_ip (read-write)
+ * remote_ip (read-write)
+ * local_mac (read-only)
+ * remote_mac (read-write)
*/
struct netconsole_target {
struct list_head list;
+#ifdef CONFIG_NETCONSOLE_DYNAMIC
+ struct config_item item;
+#endif
+ int enabled;
struct netpoll np;
};
-/* Allocate new target and setup netpoll for it */
-static struct netconsole_target *alloc_target(char *target_config)
+#ifdef CONFIG_NETCONSOLE_DYNAMIC
+
+static struct configfs_subsystem netconsole_subsys;
+
+static int __init dynamic_netconsole_init(void)
+{
+ config_group_init(&netconsole_subsys.su_group);
+ mutex_init(&netconsole_subsys.su_mutex);
+ return configfs_register_subsystem(&netconsole_subsys);
+}
+
+static void __exit dynamic_netconsole_exit(void)
+{
+ configfs_unregister_subsystem(&netconsole_subsys);
+}
+
+/*
+ * Targets that were created by parsing the boot/module option string
+ * do not exist in the configfs hierarchy (and have NULL names) and will
+ * never go away, so make these a no-op for them.
+ */
+static void netconsole_target_get(struct netconsole_target *nt)
+{
+ if (config_item_name(&nt->item))
+ config_item_get(&nt->item);
+}
+
+static void netconsole_target_put(struct netconsole_target *nt)
+{
+ if (config_item_name(&nt->item))
+ config_item_put(&nt->item);
+}
+
+#else /* !CONFIG_NETCONSOLE_DYNAMIC */
+
+static int __init dynamic_netconsole_init(void)
+{
+ return 0;
+}
+
+static void __exit dynamic_netconsole_exit(void)
+{
+}
+
+/*
+ * No danger of targets going away from under us when dynamic
+ * reconfigurability is off.
+ */
+static void netconsole_target_get(struct netconsole_target *nt)
+{
+}
+
+static void netconsole_target_put(struct netconsole_target *nt)
+{
+}
+
+#endif /* CONFIG_NETCONSOLE_DYNAMIC */
+
+/* Allocate new target (from boot/module param) and setup netpoll for it */
+static struct netconsole_target *alloc_param_target(char *target_config)
{
int err = -ENOMEM;
struct netconsole_target *nt;
- /* Allocate and initialize with defaults */
+ /*
+ * Allocate and initialize with defaults.
+ * Note that these targets get their config_item fields zeroed-out.
+ */
nt = kzalloc(sizeof(*nt), GFP_KERNEL);
if (!nt) {
printk(KERN_ERR "netconsole: failed to allocate memory\n");
@@ -106,6 +188,8 @@ static struct netconsole_target *alloc_t
if (err)
goto fail;
+ nt->enabled = 1;
+
return nt;
fail:
@@ -113,13 +197,469 @@ fail:
return ERR_PTR(err);
}
-/* Cleanup netpoll for given target and free it */
-static void free_target(struct netconsole_target *nt)
+/* Cleanup netpoll for given target (from boot/module param) and free it */
+static void free_param_target(struct netconsole_target *nt)
{
netpoll_cleanup(&nt->np);
kfree(nt);
}
+#ifdef CONFIG_NETCONSOLE_DYNAMIC
+
+/*
+ * Our subsystem hierarchy is:
+ *
+ * /sys/kernel/config/netconsole/
+ * |
+ * <target>/
+ * | enabled
+ * | dev_name
+ * | local_port
+ * | remote_port
+ * | local_ip
+ * | remote_ip
+ * | local_mac
+ * | remote_mac
+ * |
+ * <target>/...
+ */
+
+struct netconsole_target_attr {
+ struct configfs_attribute attr;
+ ssize_t (*show)(struct netconsole_target *nt,
+ char *buf);
+ ssize_t (*store)(struct netconsole_target *nt,
+ const char *buf,
+ size_t count);
+};
+
+static struct netconsole_target *to_target(struct config_item *item)
+{
+ return item ?
+ container_of(item, struct netconsole_target, item) :
+ NULL;
+}
+
+/*
+ * Wrapper over simple_strtol (base 10) with sanity and range checking.
+ * We return (signed) long only because we may want to return errors.
+ * Do not use this to convert numbers that are allowed to be negative.
+ */
+static long strtol10_check_range(const char *cp, long min, long max)
+{
+ long ret;
+ char *p = (char *) cp;
+
+ WARN_ON(min < 0);
+ WARN_ON(max < min);
+
+ ret = simple_strtol(p, &p, 10);
+
+ if (*p && (*p != '\n')) {
+ printk(KERN_ERR "netconsole: invalid input\n");
+ return -EINVAL;
+ }
+ if ((ret < min) || (ret > max)) {
+ printk(KERN_ERR "netconsole: input %ld must be between "
+ "%ld and %ld\n", ret, min, max);
+ return -EINVAL;
+ }
+
+ return ret;
+}
+
+/*
+ * Attribute operations for netconsole_target.
+ */
+
+static ssize_t show_enabled(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%d\n", nt->enabled);
+}
+
+static ssize_t show_dev_name(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%s\n", nt->np.dev_name);
+}
+
+static ssize_t show_local_port(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%d\n", nt->np.local_port);
+}
+
+static ssize_t show_remote_port(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%d\n", nt->np.remote_port);
+}
+
+static ssize_t show_local_ip(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%d.%d.%d.%d\n",
+ HIPQUAD(nt->np.local_ip));
+}
+
+static ssize_t show_remote_ip(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%d.%d.%d.%d\n",
+ HIPQUAD(nt->np.remote_ip));
+}
+
+static ssize_t show_local_mac(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%02x:%02x:%02x:%02x:%02x:%02x\n",
+ nt->np.local_mac[0], nt->np.local_mac[1],
+ nt->np.local_mac[2], nt->np.local_mac[3],
+ nt->np.local_mac[4], nt->np.local_mac[5]);
+}
+
+static ssize_t show_remote_mac(struct netconsole_target *nt, char *buf)
+{
+ return snprintf(buf, PAGE_SIZE, "%02x:%02x:%02x:%02x:%02x:%02x\n",
+ nt->np.remote_mac[0], nt->np.remote_mac[1],
+ nt->np.remote_mac[2], nt->np.remote_mac[3],
+ nt->np.remote_mac[4], nt->np.remote_mac[5]);
+}
+
+/*
+ * This one is special -- targets created through the configfs interface
+ * are not enabled (and the corresponding netpoll activated) by default.
+ * The user is expected to set the desired parameters first (which
+ * would enable him to dynamically add new netpoll targets for new
+ * network interfaces as and when they come up).
+ */
+static ssize_t store_enabled(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ int err;
+ long enabled;
+
+ enabled = strtol10_check_range(buf, 0, 1);
+ if (enabled < 0)
+ return enabled;
+
+ if (enabled) { /* 1 */
+
+ /*
+ * Skip netpoll_parse_options() -- all the attributes are
+ * already configured via configfs. Just print them out.
+ */
+ netpoll_print_options(&nt->np);
+
+ err = netpoll_setup(&nt->np);
+ if (err)
+ return err;
+
+ printk(KERN_INFO "netconsole: network logging started\n");
+
+ } else { /* 0 */
+ netpoll_cleanup(&nt->np);
+ }
+
+ nt->enabled = enabled;
+
+ return strnlen(buf, count);
+}
+
+static ssize_t store_dev_name(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ size_t len;
+
+ if (nt->enabled) {
+ printk(KERN_ERR "netconsole: target (%s) is enabled, "
+ "disable to update parameters\n",
+ config_item_name(&nt->item));
+ return -EINVAL;
+ }
+
+ strlcpy(nt->np.dev_name, buf, IFNAMSIZ);
+
+ /* Get rid of possible trailing newline from echo(1) */
+ len = strnlen(nt->np.dev_name, IFNAMSIZ);
+ if (nt->np.dev_name[len - 1] == '\n')
+ nt->np.dev_name[len - 1] = '\0';
+
+ return strnlen(buf, count);
+}
+
+static ssize_t store_local_port(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ long local_port;
+#define __U16_MAX ((__u16) ~0U)
+
+ if (nt->enabled) {
+ printk(KERN_ERR "netconsole: target (%s) is enabled, "
+ "disable to update parameters\n",
+ config_item_name(&nt->item));
+ return -EINVAL;
+ }
+
+ local_port = strtol10_check_range(buf, 0, __U16_MAX);
+ if (local_port < 0)
+ return local_port;
+
+ nt->np.local_port = local_port;
+
+ return strnlen(buf, count);
+}
+
+static ssize_t store_remote_port(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ long remote_port;
+#define __U16_MAX ((__u16) ~0U)
+
+ if (nt->enabled) {
+ printk(KERN_ERR "netconsole: target (%s) is enabled, "
+ "disable to update parameters\n",
+ config_item_name(&nt->item));
+ return -EINVAL;
+ }
+
+ remote_port = strtol10_check_range(buf, 0, __U16_MAX);
+ if (remote_port < 0)
+ return remote_port;
+
+ nt->np.remote_port = remote_port;
+
+ return strnlen(buf, count);
+}
+
+static ssize_t store_local_ip(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ if (nt->enabled) {
+ printk(KERN_ERR "netconsole: target (%s) is enabled, "
+ "disable to update parameters\n",
+ config_item_name(&nt->item));
+ return -EINVAL;
+ }
+
+ nt->np.local_ip = ntohl(in_aton(buf));
+
+ return strnlen(buf, count);
+}
+
+static ssize_t store_remote_ip(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ if (nt->enabled) {
+ printk(KERN_ERR "netconsole: target (%s) is enabled, "
+ "disable to update parameters\n",
+ config_item_name(&nt->item));
+ return -EINVAL;
+ }
+
+ nt->np.remote_ip = ntohl(in_aton(buf));
+
+ return strnlen(buf, count);
+}
+
+static ssize_t store_remote_mac(struct netconsole_target *nt,
+ const char *buf,
+ size_t count)
+{
+ u8 remote_mac[ETH_ALEN];
+ char *p = (char *) buf;
+ int i;
+
+ if (nt->enabled) {
+ printk(KERN_ERR "netconsole: target (%s) is enabled, "
+ "disable to update parameters\n",
+ config_item_name(&nt->item));
+ return -EINVAL;
+ }
+
+ for (i = 0; i < ETH_ALEN - 1; i++) {
+ remote_mac[i] = simple_strtoul(p, &p, 16);
+ if (*p != ':')
+ goto invalid;
+ p++;
+ }
+ remote_mac[ETH_ALEN - 1] = simple_strtoul(p, &p, 16);
+ if (*p && (*p != '\n'))
+ goto invalid;
+
+ memcpy(nt->np.remote_mac, remote_mac, ETH_ALEN);
+
+ return strnlen(buf, count);
+
+invalid:
+ printk(KERN_ERR "netconsole: invalid input\n");
+ return -EINVAL;
+}
+
+/*
+ * Attribute definitions for netconsole_target.
+ */
+
+#define NETCONSOLE_TARGET_ATTR_RO(_name) \
+static struct netconsole_target_attr netconsole_target_##_name = \
+ __CONFIGFS_ATTR(_name, S_IRUGO, show_##_name, NULL)
+
+#define NETCONSOLE_TARGET_ATTR_RW(_name) \
+static struct netconsole_target_attr netconsole_target_##_name = \
+ __CONFIGFS_ATTR(_name, S_IRUGO | S_IWUSR, show_##_name, store_##_name)
+
+NETCONSOLE_TARGET_ATTR_RW(enabled);
+NETCONSOLE_TARGET_ATTR_RW(dev_name);
+NETCONSOLE_TARGET_ATTR_RW(local_port);
+NETCONSOLE_TARGET_ATTR_RW(remote_port);
+NETCONSOLE_TARGET_ATTR_RW(local_ip);
+NETCONSOLE_TARGET_ATTR_RW(remote_ip);
+NETCONSOLE_TARGET_ATTR_RO(local_mac);
+NETCONSOLE_TARGET_ATTR_RW(remote_mac);
+
+static struct configfs_attribute *netconsole_target_attrs[] = {
+ &netconsole_target_enabled.attr,
+ &netconsole_target_dev_name.attr,
+ &netconsole_target_local_port.attr,
+ &netconsole_target_remote_port.attr,
+ &netconsole_target_local_ip.attr,
+ &netconsole_target_remote_ip.attr,
+ &netconsole_target_local_mac.attr,
+ &netconsole_target_remote_mac.attr,
+ NULL,
+};
+
+/*
+ * Item operations and type for netconsole_target.
+ */
+
+static void netconsole_target_release(struct config_item *item)
+{
+ kfree(to_target(item));
+}
+
+static ssize_t netconsole_target_attr_show(struct config_item *item,
+ struct configfs_attribute *attr,
+ char *buf)
+{
+ ssize_t ret = -EINVAL;
+ struct netconsole_target *nt = to_target(item);
+ struct netconsole_target_attr *na =
+ container_of(attr, struct netconsole_target_attr, attr);
+
+ if (na->show)
+ ret = na->show(nt, buf);
+
+ return ret;
+}
+
+static ssize_t netconsole_target_attr_store(struct config_item *item,
+ struct configfs_attribute *attr,
+ const char *buf,
+ size_t count)
+{
+ ssize_t ret = -EINVAL;
+ struct netconsole_target *nt = to_target(item);
+ struct netconsole_target_attr *na =
+ container_of(attr, struct netconsole_target_attr, attr);
+
+ if (na->store)
+ ret = na->store(nt, buf, count);
+
+ return ret;
+}
+
+static struct configfs_item_operations netconsole_target_item_ops = {
+ .release = netconsole_target_release,
+ .show_attribute = netconsole_target_attr_show,
+ .store_attribute = netconsole_target_attr_store,
+};
+
+static struct config_item_type netconsole_target_type = {
+ .ct_attrs = netconsole_target_attrs,
+ .ct_item_ops = &netconsole_target_item_ops,
+ .ct_owner = THIS_MODULE,
+};
+
+/*
+ * Group operations and type for netconsole_subsys.
+ */
+
+static struct config_item *make_netconsole_target(struct config_group *group,
+ const char *name)
+{
+ unsigned long flags;
+ struct netconsole_target *nt;
+
+ /*
+ * Allocate and initialize with defaults.
+ * Target is disabled at creation (enabled == 0).
+ */
+ nt = kzalloc(sizeof(*nt), GFP_KERNEL);
+ if (!nt) {
+ printk(KERN_ERR "netconsole: failed to allocate memory\n");
+ return NULL;
+ }
+
+ nt->np.name = "netconsole";
+ strlcpy(nt->np.dev_name, "eth0", IFNAMSIZ);
+ nt->np.local_port = 6665;
+ nt->np.remote_port = 6666;
+ memset(nt->np.remote_mac, 0xff, ETH_ALEN);
+
+ /* Initialize the config_item member */
+ config_item_init_type_name(&nt->item, name, &netconsole_target_type);
+
+ /* Adding, but it is disabled */
+ spin_lock_irqsave(&target_list_lock, flags);
+ list_add(&nt->list, &target_list);
+ spin_unlock_irqrestore(&target_list_lock, flags);
+
+ return &nt->item;
+}
+
+static void drop_netconsole_target(struct config_group *group,
+ struct config_item *item)
+{
+ unsigned long flags;
+ struct netconsole_target *nt = to_target(item);
+
+ spin_lock_irqsave(&target_list_lock, flags);
+ list_del(&nt->list);
+ spin_unlock_irqrestore(&target_list_lock, flags);
+
+ /*
+ * The target may have never been enabled, or was manually disabled
+ * before being removed so netpoll may have already been cleaned up.
+ */
+ if (nt->enabled)
+ netpoll_cleanup(&nt->np);
+
+ config_item_put(&nt->item);
+}
+
+static struct configfs_group_operations netconsole_subsys_group_ops = {
+ .make_item = make_netconsole_target,
+ .drop_item = drop_netconsole_target,
+};
+
+static struct config_item_type netconsole_subsys_type = {
+ .ct_group_ops = &netconsole_subsys_group_ops,
+ .ct_owner = THIS_MODULE,
+};
+
+/* The netconsole configfs subsystem */
+static struct configfs_subsystem netconsole_subsys = {
+ .su_group = {
+ .cg_item = {
+ .ci_namebuf = "netconsole",
+ .ci_type = &netconsole_subsys_type,
+ },
+ },
+};
+
+#endif /* CONFIG_NETCONSOLE_DYNAMIC */
+
/* Handle network interface device notifications */
static int netconsole_netdev_event(struct notifier_block *this,
unsigned long event,
@@ -134,6 +674,7 @@ static int netconsole_netdev_event(struc
spin_lock_irqsave(&target_list_lock, flags);
list_for_each_entry(nt, &target_list, list) {
+ netconsole_target_get(nt);
if (nt->np.dev == dev) {
switch (event) {
case NETDEV_CHANGEADDR:
@@ -145,6 +686,7 @@ static int netconsole_netdev_event(struc
break;
}
}
+ netconsole_target_put(nt);
}
spin_unlock_irqrestore(&target_list_lock, flags);
@@ -169,7 +711,8 @@ static void write_msg(struct console *co
spin_lock_irqsave(&target_list_lock, flags);
list_for_each_entry(nt, &target_list, list) {
- if (netif_running(nt->np.dev)) {
+ netconsole_target_get(nt);
+ if (nt->enabled && netif_running(nt->np.dev)) {
/*
* We nest this inside the for-each-target loop above
* so that we're able to get as much logging out to
@@ -184,6 +727,7 @@ static void write_msg(struct console *co
left -= frag;
}
}
+ netconsole_target_put(nt);
}
spin_unlock_irqrestore(&target_list_lock, flags);
}
@@ -196,48 +740,52 @@ static struct console netconsole = {
static int __init init_netconsole(void)
{
- int err = 0;
+ int err;
struct netconsole_target *nt, *tmp;
unsigned long flags;
char *target_config;
char *input = config;
- if (!strnlen(input, MAX_PARAM_LENGTH)) {
- printk(KERN_INFO "netconsole: not configured, aborting\n");
- goto out;
- }
-
- while ((target_config = strsep(&input, ";"))) {
- nt = alloc_target(target_config);
- if (IS_ERR(nt)) {
- err = PTR_ERR(nt);
- goto fail;
+ if (strnlen(input, MAX_PARAM_LENGTH)) {
+ while ((target_config = strsep(&input, ";"))) {
+ nt = alloc_param_target(target_config);
+ if (IS_ERR(nt)) {
+ err = PTR_ERR(nt);
+ goto fail;
+ }
+ spin_lock_irqsave(&target_list_lock, flags);
+ list_add(&nt->list, &target_list);
+ spin_unlock_irqrestore(&target_list_lock, flags);
}
- spin_lock_irqsave(&target_list_lock, flags);
- list_add(&nt->list, &target_list);
- spin_unlock_irqrestore(&target_list_lock, flags);
}
err = register_netdevice_notifier(&netconsole_netdev_notifier);
if (err)
goto fail;
+ err = dynamic_netconsole_init();
+ if (err)
+ goto undonotifier;
+
register_console(&netconsole);
printk(KERN_INFO "netconsole: network logging started\n");
-out:
return err;
+undonotifier:
+ unregister_netdevice_notifier(&netconsole_netdev_notifier);
+
fail:
printk(KERN_ERR "netconsole: cleaning up\n");
/*
- * Remove all targets and destroy them. Skipping the list
+ * Remove all targets and destroy them (only targets created
+ * from the boot/module option exist here). Skipping the list
* lock is safe here, and netpoll_cleanup() will sleep.
*/
list_for_each_entry_safe(nt, tmp, &target_list, list) {
list_del(&nt->list);
- free_target(nt);
+ free_param_target(nt);
}
return err;
@@ -248,15 +796,20 @@ static void __exit cleanup_netconsole(vo
struct netconsole_target *nt, *tmp;
unregister_console(&netconsole);
+ dynamic_netconsole_exit();
unregister_netdevice_notifier(&netconsole_netdev_notifier);
/*
- * Remove all targets and destroy them. Skipping the list
- * lock is safe here, and netpoll_cleanup() will sleep.
+ * Targets created via configfs pin references on our module
+ * and would first be rmdir(2)'ed from userspace. We reach
+ * here only when they are already destroyed, and only those
+ * created from the boot/module option are left, so remove and
+ * destroy them. Skipping the list lock is safe here, and
+ * netpoll_cleanup() will sleep.
*/
list_for_each_entry_safe(nt, tmp, &target_list, list) {
list_del(&nt->list);
- free_target(nt);
+ free_param_target(nt);
}
}
diff -puN include/linux/netpoll.h~netconsole-support-dynamic-reconfiguration-using-configfs include/linux/netpoll.h
--- a/include/linux/netpoll.h~netconsole-support-dynamic-reconfiguration-using-configfs
+++ a/include/linux/netpoll.h
@@ -35,6 +35,7 @@ struct netpoll_info {
void netpoll_poll(struct netpoll *np);
void netpoll_send_udp(struct netpoll *np, const char *msg, int len);
+void netpoll_print_options(struct netpoll *np);
int netpoll_parse_options(struct netpoll *np, char *opt);
int netpoll_setup(struct netpoll *np);
int netpoll_trap(void);
diff -puN net/core/netpoll.c~netconsole-support-dynamic-reconfiguration-using-configfs net/core/netpoll.c
--- a/net/core/netpoll.c~netconsole-support-dynamic-reconfiguration-using-configfs
+++ a/net/core/netpoll.c
@@ -532,6 +532,29 @@ out:
return 0;
}
+void netpoll_print_options(struct netpoll *np)
+{
+ printk(KERN_INFO "%s: local port %d\n",
+ np->name, np->local_port);
+ printk(KERN_INFO "%s: local IP %d.%d.%d.%d\n",
+ np->name, HIPQUAD(np->local_ip));
+ printk(KERN_INFO "%s: interface %s\n",
+ np->name, np->dev_name);
+ printk(KERN_INFO "%s: remote port %d\n",
+ np->name, np->remote_port);
+ printk(KERN_INFO "%s: remote IP %d.%d.%d.%d\n",
+ np->name, HIPQUAD(np->remote_ip));
+ printk(KERN_INFO "%s: remote ethernet address "
+ "%02x:%02x:%02x:%02x:%02x:%02x\n",
+ np->name,
+ np->remote_mac[0],
+ np->remote_mac[1],
+ np->remote_mac[2],
+ np->remote_mac[3],
+ np->remote_mac[4],
+ np->remote_mac[5]);
+}
+
int netpoll_parse_options(struct netpoll *np, char *opt)
{
char *cur=opt, *delim;
@@ -544,7 +567,6 @@ int netpoll_parse_options(struct netpoll
cur = delim;
}
cur++;
- printk(KERN_INFO "%s: local port %d\n", np->name, np->local_port);
if (*cur != '/') {
if ((delim = strchr(cur, '/')) == NULL)
@@ -552,9 +574,6 @@ int netpoll_parse_options(struct netpoll
*delim = 0;
np->local_ip = ntohl(in_aton(cur));
cur = delim;
-
- printk(KERN_INFO "%s: local IP %d.%d.%d.%d\n",
- np->name, HIPQUAD(np->local_ip));
}
cur++;
@@ -568,8 +587,6 @@ int netpoll_parse_options(struct netpoll
}
cur++;
- printk(KERN_INFO "%s: interface %s\n", np->name, np->dev_name);
-
if (*cur != '@') {
/* dst port */
if ((delim = strchr(cur, '@')) == NULL)
@@ -579,7 +596,6 @@ int netpoll_parse_options(struct netpoll
cur = delim;
}
cur++;
- printk(KERN_INFO "%s: remote port %d\n", np->name, np->remote_port);
/* dst ip */
if ((delim = strchr(cur, '/')) == NULL)
@@ -588,9 +604,6 @@ int netpoll_parse_options(struct netpoll
np->remote_ip = ntohl(in_aton(cur));
cur = delim + 1;
- printk(KERN_INFO "%s: remote IP %d.%d.%d.%d\n",
- np->name, HIPQUAD(np->remote_ip));
-
if (*cur != 0) {
/* MAC address */
if ((delim = strchr(cur, ':')) == NULL)
@@ -621,15 +634,7 @@ int netpoll_parse_options(struct netpoll
np->remote_mac[5] = simple_strtol(cur, NULL, 16);
}
- printk(KERN_INFO "%s: remote ethernet address "
- "%02x:%02x:%02x:%02x:%02x:%02x\n",
- np->name,
- np->remote_mac[0],
- np->remote_mac[1],
- np->remote_mac[2],
- np->remote_mac[3],
- np->remote_mac[4],
- np->remote_mac[5]);
+ netpoll_print_options(np);
return 0;
@@ -831,6 +836,7 @@ void netpoll_set_trap(int trap)
EXPORT_SYMBOL(netpoll_set_trap);
EXPORT_SYMBOL(netpoll_trap);
+EXPORT_SYMBOL(netpoll_print_options);
EXPORT_SYMBOL(netpoll_parse_options);
EXPORT_SYMBOL(netpoll_setup);
EXPORT_SYMBOL(netpoll_cleanup);
_
^ permalink raw reply
* [patch 17/18] 3c59x: fix duplex configuration
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, klassert, mb-tmp-ohtmvyyn.xreary.bet, protasnb
From: Steffen Klassert <klassert@mathematik.tu-chemnitz.de>
A special sequence of ifconfig up/down and plug/unplug the cable can break
the duplex configuration of the driver.
Setting
vp->mii.full_duplex = vp->full_duplex
in vortex_up should fix this.
Addresses Bug 8575 3c59x duplex configuration broken
http://bugzilla.kernel.org/show_bug.cgi?id=8575
Cc: Martin Buck <mb-tmp-ohtmvyyn.xreary.bet@gromit.dyndns.org>
Signed-off-by: Steffen Klassert <klassert@mathematik.tu-chemnitz.de>
Cc: Natalie Protasevich <protasnb@gmail.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/3c59x.c | 1 +
1 files changed, 1 insertion(+)
diff -puN drivers/net/3c59x.c~3c59x-fix-duplex-configuration drivers/net/3c59x.c
--- a/drivers/net/3c59x.c~3c59x-fix-duplex-configuration
+++ a/drivers/net/3c59x.c
@@ -1559,6 +1559,7 @@ vortex_up(struct net_device *dev)
mii_reg1 = mdio_read(dev, vp->phys[0], MII_BMSR);
mii_reg5 = mdio_read(dev, vp->phys[0], MII_LPA);
vp->partner_flow_ctrl = ((mii_reg5 & 0x0400) != 0);
+ vp->mii.full_duplex = vp->full_duplex;
vortex_check_media(dev, 1);
}
_
^ permalink raw reply
* [patch 14/18] uli526x: add suspend and resume routines
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, rjw, grundler, kyle
From: Rafael J. Wysocki <rjw@sisk.pl>
Add suspend/resume support to the uli526x network driver (tested on x86_64,
with "Ethernet controller: ALi Corporation M5263 Ethernet Controller, rev 40").
This patch is based on the suspend/resume code in the tg3 driver.
Signed-off-by: Rafael J. Wysocki <rjw@sisk.pl>
Acked-by: Grant Grundler <grundler@parisc-linux.org>
Cc: Kyle McMartin <kyle@mcmartin.ca>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/tulip/uli526x.c | 109 ++++++++++++++++++++++++++++++++--
1 files changed, 103 insertions(+), 6 deletions(-)
diff -puN drivers/net/tulip/uli526x.c~uli526x-add-suspend-and-resume-routines drivers/net/tulip/uli526x.c
--- a/drivers/net/tulip/uli526x.c~uli526x-add-suspend-and-resume-routines
+++ a/drivers/net/tulip/uli526x.c
@@ -1110,19 +1110,15 @@ static void uli526x_timer(unsigned long
/*
- * Dynamic reset the ULI526X board
* Stop ULI526X board
* Free Tx/Rx allocated memory
- * Reset ULI526X board
- * Re-initialize ULI526X board
+ * Init system variable
*/
-static void uli526x_dynamic_reset(struct net_device *dev)
+static void uli526x_reset_prepare(struct net_device *dev)
{
struct uli526x_board_info *db = netdev_priv(dev);
- ULI526X_DBUG(0, "uli526x_dynamic_reset()", 0);
-
/* Sopt MAC controller */
db->cr6_data &= ~(CR6_RXSC | CR6_TXSC); /* Disable Tx/Rx */
update_cr6(db->cr6_data, dev->base_addr);
@@ -1141,6 +1137,22 @@ static void uli526x_dynamic_reset(struct
db->link_failed = 1;
db->init=1;
db->wait_reset = 0;
+}
+
+
+/*
+ * Dynamic reset the ULI526X board
+ * Stop ULI526X board
+ * Free Tx/Rx allocated memory
+ * Reset ULI526X board
+ * Re-initialize ULI526X board
+ */
+
+static void uli526x_dynamic_reset(struct net_device *dev)
+{
+ ULI526X_DBUG(0, "uli526x_dynamic_reset()", 0);
+
+ uli526x_reset_prepare(dev);
/* Re-initialize ULI526X board */
uli526x_init(dev);
@@ -1150,6 +1162,89 @@ static void uli526x_dynamic_reset(struct
}
+#ifdef CONFIG_PM_SLEEP
+
+/*
+ * Suspend the interface.
+ */
+
+static int uli526x_suspend(struct pci_dev *pdev, pm_message_t state)
+{
+ struct net_device *dev = pci_get_drvdata(pdev);
+ pci_power_t power_state;
+ int err;
+
+ ULI526X_DBUG(0, "uli526x_suspend", 0);
+
+ if (!(dev && netdev_priv(dev)))
+ return 0;
+
+ pci_save_state(pdev);
+
+ if (!netif_running(dev))
+ return 0;
+
+ netif_device_detach(dev);
+ uli526x_reset_prepare(dev);
+
+ power_state = pci_choose_state(pdev, state);
+ pci_enable_wake(pdev, power_state, 0);
+ err = pci_set_power_state(pdev, power_state);
+ if (err) {
+ netif_device_attach(dev);
+ /* Re-initialize ULI526X board */
+ uli526x_init(dev);
+ /* Restart upper layer interface */
+ netif_wake_queue(dev);
+ }
+
+ return err;
+}
+
+/*
+ * Resume the interface.
+ */
+
+static int uli526x_resume(struct pci_dev *pdev)
+{
+ struct net_device *dev = pci_get_drvdata(pdev);
+ struct uli526x_board_info *db = netdev_priv(dev);
+ int err;
+
+ ULI526X_DBUG(0, "uli526x_resume", 0);
+
+ if (!(dev && db))
+ return 0;
+
+ pci_restore_state(pdev);
+
+ if (!netif_running(dev))
+ return 0;
+
+ err = pci_set_power_state(pdev, PCI_D0);
+ if (err) {
+ printk(KERN_WARNING "%s: Could not put device into D0\n",
+ dev->name);
+ return err;
+ }
+
+ netif_device_attach(dev);
+ /* Re-initialize ULI526X board */
+ uli526x_init(dev);
+ /* Restart upper layer interface */
+ netif_wake_queue(dev);
+
+ return 0;
+}
+
+#else /* !CONFIG_PM_SLEEP */
+
+#define uli526x_suspend NULL
+#define uli526x_resume NULL
+
+#endif /* !CONFIG_PM_SLEEP */
+
+
/*
* free all allocated rx buffer
*/
@@ -1689,6 +1784,8 @@ static struct pci_driver uli526x_driver
.id_table = uli526x_pci_tbl,
.probe = uli526x_init_one,
.remove = __devexit_p(uli526x_remove_one),
+ .suspend = uli526x_suspend,
+ .resume = uli526x_resume,
};
MODULE_AUTHOR("Peer Chen, peer.chen@uli.com.tw");
_
^ permalink raw reply
* [patch 12/18] e1000: #if 0 two functions
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, bunk, auke-jan.h.kok
From: Adrian Bunk <bunk@stusta.de>
e1000_{read,write}_pci_cfg() are no longer used.
Signed-off-by: Adrian Bunk <bunk@stusta.de>
Cc: Auke Kok <auke-jan.h.kok@intel.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/e1000/e1000_hw.h | 2 --
drivers/net/e1000/e1000_main.c | 4 ++++
2 files changed, 4 insertions(+), 2 deletions(-)
diff -puN drivers/net/e1000/e1000_hw.h~e1000-if-0-two-functions drivers/net/e1000/e1000_hw.h
--- a/drivers/net/e1000/e1000_hw.h~e1000-if-0-two-functions
+++ a/drivers/net/e1000/e1000_hw.h
@@ -421,8 +421,6 @@ void e1000_tbi_adjust_stats(struct e1000
void e1000_get_bus_info(struct e1000_hw *hw);
void e1000_pci_set_mwi(struct e1000_hw *hw);
void e1000_pci_clear_mwi(struct e1000_hw *hw);
-void e1000_read_pci_cfg(struct e1000_hw *hw, uint32_t reg, uint16_t * value);
-void e1000_write_pci_cfg(struct e1000_hw *hw, uint32_t reg, uint16_t * value);
int32_t e1000_read_pcie_cap_reg(struct e1000_hw *hw, uint32_t reg, uint16_t *value);
void e1000_pcix_set_mmrbc(struct e1000_hw *hw, int mmrbc);
int e1000_pcix_get_mmrbc(struct e1000_hw *hw);
diff -puN drivers/net/e1000/e1000_main.c~e1000-if-0-two-functions drivers/net/e1000/e1000_main.c
--- a/drivers/net/e1000/e1000_main.c~e1000-if-0-two-functions
+++ a/drivers/net/e1000/e1000_main.c
@@ -4890,6 +4890,8 @@ e1000_pci_clear_mwi(struct e1000_hw *hw)
pci_clear_mwi(adapter->pdev);
}
+#if 0
+
void
e1000_read_pci_cfg(struct e1000_hw *hw, uint32_t reg, uint16_t *value)
{
@@ -4906,6 +4908,8 @@ e1000_write_pci_cfg(struct e1000_hw *hw,
pci_write_config_word(adapter->pdev, reg, *value);
}
+#endif /* 0 */
+
int
e1000_pcix_get_mmrbc(struct e1000_hw *hw)
{
_
^ permalink raw reply
* [patch 13/18] natsemi: fix netdev error acounting
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, loveminix, protasnb, thockin
From: Andrew Morton <akpm@linux-foundation.org>
When a detailed netdev error is counted, we also must account for it in the
aggregated error count.
Addresses http://bugzilla.kernel.org/show_bug.cgi?id=8106
Cc: Tim Hockin <thockin@hockin.org>
Cc: Jeff Garzik <jeff@garzik.org>
Cc: Chongfeng Hu <loveminix@yahoo.com.cn>
Cc: Natalie Protasevich <protasnb@gmail.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/natsemi.c | 3 +++
1 files changed, 3 insertions(+)
diff -puN drivers/net/natsemi.c~natsemi-fix-netdev-error-acounting drivers/net/natsemi.c
--- a/drivers/net/natsemi.c~natsemi-fix-netdev-error-acounting
+++ a/drivers/net/natsemi.c
@@ -2438,13 +2438,16 @@ static void netdev_error(struct net_devi
dev->name);
}
np->stats.rx_fifo_errors++;
+ np->stats.rx_errors++;
}
/* Hmmmmm, it's not clear how to recover from PCI faults. */
if (intr_status & IntrPCIErr) {
printk(KERN_NOTICE "%s: PCI error %#08x\n", dev->name,
intr_status & IntrPCIErr);
np->stats.tx_fifo_errors++;
+ np->stats.tx_errors++;
np->stats.rx_fifo_errors++;
+ np->stats.rx_errors++;
}
spin_unlock(&np->lock);
}
_
^ permalink raw reply
* [patch 25/28] netconsole: Support multiple logging targets
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
This patch introduces support for multiple targets, independent of
CONFIG_NETCONSOLE_DYNAMIC -- this is useful even in the default case and
(including the infrastructure introduced in previous patches) doesn't really
add too many bytes to module text. All the complexity (and size) comes with
the dynamic reconfigurability / userspace interface patch, and so it's
plausible users may want to keep this enabled but that disabled (say to avoid
a dependency on CONFIG_CONFIGFS_FS too).
Also update documentation to mention the use of ";" separator to specify
multiple logging targets in the boot/module option string.
Brief overview:
We maintain a target_list (and corresponding lock). Get rid of the static
"default_target" and introduce allocation and release functions for our
netconsole_target objects (but keeping sure to preserve previous behaviour
such as default values). During init_netconsole(), ";" is used as the
separator to identify multiple target specifications in the boot/module option
string. The target specifications are parsed and netpolls setup. During
exit, the target_list is torn down and all items released.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Cc: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
Documentation/networking/netconsole.txt | 6
drivers/net/netconsole.c | 171 ++++++++++++++++------
2 files changed, 137 insertions(+), 40 deletions(-)
diff -puN Documentation/networking/netconsole.txt~netconsole-support-multiple-logging-targets Documentation/networking/netconsole.txt
--- a/Documentation/networking/netconsole.txt~netconsole-support-multiple-logging-targets
+++ a/Documentation/networking/netconsole.txt
@@ -34,6 +34,12 @@ Examples:
insmod netconsole netconsole=@/,@10.0.0.2/
+It also supports logging to multiple remote agents by specifying
+parameters for the multiple agents separated by semicolons and the
+complete string enclosed in "quotes", thusly:
+
+ modprobe netconsole netconsole="@/,@10.0.0.2/;@/eth1,6892@10.0.0.3/"
+
Built-in netconsole starts immediately after the TCP stack is
initialized and attempts to bring up the supplied dev at the supplied
address.
diff -puN drivers/net/netconsole.c~netconsole-support-multiple-logging-targets drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-support-multiple-logging-targets
+++ a/drivers/net/netconsole.c
@@ -62,44 +62,93 @@ static int __init option_setup(char *opt
__setup("netconsole=", option_setup);
#endif /* MODULE */
+/* Linked list of all configured targets */
+static LIST_HEAD(target_list);
+
+/* This needs to be a spinlock because write_msg() cannot sleep */
+static DEFINE_SPINLOCK(target_list_lock);
+
/**
* struct netconsole_target - Represents a configured netconsole target.
+ * @list: Links this target into the target_list.
* @np: The netpoll structure for this target.
*/
struct netconsole_target {
+ struct list_head list;
struct netpoll np;
};
-static struct netconsole_target default_target = {
- .np = {
- .name = "netconsole",
- .dev_name = "eth0",
- .local_port = 6665,
- .remote_port = 6666,
- .remote_mac = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
- },
-};
+/* Allocate new target and setup netpoll for it */
+static struct netconsole_target *alloc_target(char *target_config)
+{
+ int err = -ENOMEM;
+ struct netconsole_target *nt;
+
+ /* Allocate and initialize with defaults */
+ nt = kzalloc(sizeof(*nt), GFP_KERNEL);
+ if (!nt) {
+ printk(KERN_ERR "netconsole: failed to allocate memory\n");
+ goto fail;
+ }
+
+ nt->np.name = "netconsole";
+ strlcpy(nt->np.dev_name, "eth0", IFNAMSIZ);
+ nt->np.local_port = 6665;
+ nt->np.remote_port = 6666;
+ memset(nt->np.remote_mac, 0xff, ETH_ALEN);
+
+ /* Parse parameters and setup netpoll */
+ err = netpoll_parse_options(&nt->np, target_config);
+ if (err)
+ goto fail;
+
+ err = netpoll_setup(&nt->np);
+ if (err)
+ goto fail;
+
+ return nt;
+
+fail:
+ kfree(nt);
+ return ERR_PTR(err);
+}
+
+/* Cleanup netpoll for given target and free it */
+static void free_target(struct netconsole_target *nt)
+{
+ netpoll_cleanup(&nt->np);
+ kfree(nt);
+}
/* Handle network interface device notifications */
static int netconsole_netdev_event(struct notifier_block *this,
unsigned long event,
void *ptr)
{
+ unsigned long flags;
+ struct netconsole_target *nt;
struct net_device *dev = ptr;
- struct netconsole_target *nt = &default_target;
- if (nt->np.dev == dev) {
- switch (event) {
- case NETDEV_CHANGEADDR:
- memcpy(nt->np.local_mac, dev->dev_addr, ETH_ALEN);
- break;
-
- case NETDEV_CHANGENAME:
- strlcpy(nt->np.dev_name, dev->name, IFNAMSIZ);
- break;
+ if (!(event == NETDEV_CHANGEADDR || event == NETDEV_CHANGENAME))
+ goto done;
+
+ spin_lock_irqsave(&target_list_lock, flags);
+ list_for_each_entry(nt, &target_list, list) {
+ if (nt->np.dev == dev) {
+ switch (event) {
+ case NETDEV_CHANGEADDR:
+ memcpy(nt->np.local_mac, dev->dev_addr, ETH_ALEN);
+ break;
+
+ case NETDEV_CHANGENAME:
+ strlcpy(nt->np.dev_name, dev->name, IFNAMSIZ);
+ break;
+ }
}
}
+ spin_unlock_irqrestore(&target_list_lock, flags);
+done:
return NOTIFY_DONE;
}
@@ -111,18 +160,32 @@ static void write_msg(struct console *co
{
int frag, left;
unsigned long flags;
- struct netconsole_target *nt = &default_target;
+ struct netconsole_target *nt;
+ const char *tmp;
- if (netif_running(nt->np.dev)) {
- local_irq_save(flags);
- for (left = len; left;) {
- frag = min(left, MAX_PRINT_CHUNK);
- netpoll_send_udp(&nt->np, msg, frag);
- msg += frag;
- left -= frag;
+ /* Avoid taking lock and disabling interrupts unnecessarily */
+ if (list_empty(&target_list))
+ return;
+
+ spin_lock_irqsave(&target_list_lock, flags);
+ list_for_each_entry(nt, &target_list, list) {
+ if (netif_running(nt->np.dev)) {
+ /*
+ * We nest this inside the for-each-target loop above
+ * so that we're able to get as much logging out to
+ * at least one target if we die inside here, instead
+ * of unnecessarily keeping all targets in lock-step.
+ */
+ tmp = msg;
+ for (left = len; left;) {
+ frag = min(left, MAX_PRINT_CHUNK);
+ netpoll_send_udp(&nt->np, tmp, frag);
+ tmp += frag;
+ left -= frag;
+ }
}
- local_irq_restore(flags);
}
+ spin_unlock_irqrestore(&target_list_lock, flags);
}
static struct console netconsole = {
@@ -134,39 +197,67 @@ static struct console netconsole = {
static int __init init_netconsole(void)
{
int err = 0;
- struct netconsole_target *nt = &default_target;
+ struct netconsole_target *nt, *tmp;
+ unsigned long flags;
+ char *target_config;
+ char *input = config;
- if (!strnlen(config, MAX_PARAM_LENGTH)) {
+ if (!strnlen(input, MAX_PARAM_LENGTH)) {
printk(KERN_INFO "netconsole: not configured, aborting\n");
goto out;
}
- err = netpoll_parse_options(&nt->np, config);
- if (err)
- goto out;
-
- err = netpoll_setup(&nt->np);
- if (err)
- goto out;
+ while ((target_config = strsep(&input, ";"))) {
+ nt = alloc_target(target_config);
+ if (IS_ERR(nt)) {
+ err = PTR_ERR(nt);
+ goto fail;
+ }
+ spin_lock_irqsave(&target_list_lock, flags);
+ list_add(&nt->list, &target_list);
+ spin_unlock_irqrestore(&target_list_lock, flags);
+ }
err = register_netdevice_notifier(&netconsole_netdev_notifier);
if (err)
- goto out;
+ goto fail;
register_console(&netconsole);
printk(KERN_INFO "netconsole: network logging started\n");
out:
return err;
+
+fail:
+ printk(KERN_ERR "netconsole: cleaning up\n");
+
+ /*
+ * Remove all targets and destroy them. Skipping the list
+ * lock is safe here, and netpoll_cleanup() will sleep.
+ */
+ list_for_each_entry_safe(nt, tmp, &target_list, list) {
+ list_del(&nt->list);
+ free_target(nt);
+ }
+
+ return err;
}
static void __exit cleanup_netconsole(void)
{
- struct netconsole_target *nt = &default_target;
+ struct netconsole_target *nt, *tmp;
unregister_console(&netconsole);
unregister_netdevice_notifier(&netconsole_netdev_notifier);
- netpoll_cleanup(&nt->np);
+
+ /*
+ * Remove all targets and destroy them. Skipping the list
+ * lock is safe here, and netpoll_cleanup() will sleep.
+ */
+ list_for_each_entry_safe(nt, tmp, &target_list, list) {
+ list_del(&nt->list);
+ free_target(nt);
+ }
}
module_init(init_netconsole);
_
^ permalink raw reply
* [patch 23/28] netconsole: Introduce netconsole_target
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
Introduce a wrapper structure over netpoll to represent logging targets
configured in netconsole. This will get extended with other members in
further patches.
This is done independent of the (to-be-introduced) NETCONSOLE_DYNAMIC config
option so that we're able to drastically cut down on the #ifdef complexity of
final netconsole.c. Also, struct netconsole_target would be required for
multiple targets support also, and not just dynamic reconfigurability.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Cc: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 36 +++++++++++++++++++++++++-----------
1 files changed, 25 insertions(+), 11 deletions(-)
diff -puN drivers/net/netconsole.c~netconsole-introduce-netconsole_target drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-introduce-netconsole_target
+++ a/drivers/net/netconsole.c
@@ -62,24 +62,35 @@ static int __init option_setup(char *opt
__setup("netconsole=", option_setup);
#endif /* MODULE */
-static struct netpoll np = {
- .name = "netconsole",
- .dev_name = "eth0",
- .local_port = 6665,
- .remote_port = 6666,
- .remote_mac = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
+/**
+ * struct netconsole_target - Represents a configured netconsole target.
+ * @np: The netpoll structure for this target.
+ */
+struct netconsole_target {
+ struct netpoll np;
+};
+
+static struct netconsole_target default_target = {
+ .np = {
+ .name = "netconsole",
+ .dev_name = "eth0",
+ .local_port = 6665,
+ .remote_port = 6666,
+ .remote_mac = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
+ },
};
static void write_msg(struct console *con, const char *msg, unsigned int len)
{
int frag, left;
unsigned long flags;
+ struct netconsole_target *nt = &default_target;
- if (netif_running(np.dev)) {
+ if (netif_running(nt->np.dev)) {
local_irq_save(flags);
for (left = len; left;) {
frag = min(left, MAX_PRINT_CHUNK);
- netpoll_send_udp(&np, msg, frag);
+ netpoll_send_udp(&nt->np, msg, frag);
msg += frag;
left -= frag;
}
@@ -96,17 +107,18 @@ static struct console netconsole = {
static int __init init_netconsole(void)
{
int err = 0;
+ struct netconsole_target *nt = &default_target;
if (!strnlen(config, MAX_PARAM_LENGTH)) {
printk(KERN_INFO "netconsole: not configured, aborting\n");
goto out;
}
- err = netpoll_parse_options(&np, config);
+ err = netpoll_parse_options(&nt->np, config);
if (err)
goto out;
- err = netpoll_setup(&np);
+ err = netpoll_setup(&nt->np);
if (err)
goto out;
@@ -119,8 +131,10 @@ out:
static void __exit cleanup_netconsole(void)
{
+ struct netconsole_target *nt = &default_target;
+
unregister_console(&netconsole);
- netpoll_cleanup(&np);
+ netpoll_cleanup(&nt->np);
}
module_init(init_netconsole);
_
^ permalink raw reply
* [patch 20/28] netconsole: Simplify boot/module option setup logic
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
Presently, boot/module parameters are set up quite differently for the case of
built-in netconsole (__setup() -> obsolete_checksetup() ->
netpoll_parse_options() -> strlen(config) == 0 in init_netconsole()) vs
modular netconsole (module_param_string() -> string copied to the config
variable -> strlen(config) != 0 init_netconsole() -> netpoll_parse_options()).
This patch makes both of them similar by doing exactly the equivalent of a
module_param_string() in option_setup() also -- just copying the param string
passed from the kernel command line into "config" variable. So,
strlen(config) != 0 in both cases, and netpoll_parse_options() is always
called from init_netconsole(), thus making the setup logic for both cases
similar.
Now, option_setup() is only ever called / used for the built-in case, so we
put it inside a #ifndef MODULE, otherwise gcc will complain about
option_setup() being "defined but not used". Also, the "configured" variable
is redundant with this patch and hence removed.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Acked-by: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 27 ++++++++++++++-------------
1 files changed, 14 insertions(+), 13 deletions(-)
diff -puN drivers/net/netconsole.c~netconsole-simplify-boot-module-option-setup-logic drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-simplify-boot-module-option-setup-logic
+++ a/drivers/net/netconsole.c
@@ -53,6 +53,15 @@ static char config[MAX_PARAM_LENGTH];
module_param_string(netconsole, config, MAX_PARAM_LENGTH, 0);
MODULE_PARM_DESC(netconsole, " netconsole=[src-port]@[src-ip]/[dev],[tgt-port]@<tgt-ip>/[tgt-macaddr]\n");
+#ifndef MODULE
+static int __init option_setup(char *opt)
+{
+ strlcpy(config, opt, MAX_PARAM_LENGTH);
+ return 1;
+}
+__setup("netconsole=", option_setup);
+#endif /* MODULE */
+
static struct netpoll np = {
.name = "netconsole",
.dev_name = "eth0",
@@ -60,7 +69,6 @@ static struct netpoll np = {
.remote_port = 6666,
.remote_mac = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
};
-static int configured;
static void write_msg(struct console *con, const char *msg, unsigned int len)
{
@@ -85,26 +93,19 @@ static struct console netconsole = {
.write = write_msg,
};
-static int __init option_setup(char *opt)
-{
- configured = !netpoll_parse_options(&np, opt);
- return 1;
-}
-
-__setup("netconsole=", option_setup);
-
static int __init init_netconsole(void)
{
int err = 0;
- if (strnlen(config, MAX_PARAM_LENGTH))
- option_setup(config);
-
- if (!configured) {
+ if (!strnlen(config, MAX_PARAM_LENGTH)) {
printk(KERN_INFO "netconsole: not configured, aborting\n");
goto out;
}
+ err = netpoll_parse_options(&np, config);
+ if (err)
+ goto out;
+
err = netpoll_setup(&np);
if (err)
goto out;
_
^ permalink raw reply
* [patch 24/28] netconsole: Introduce netconsole_netdev_notifier
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
To update fields of underlying netpoll structure at runtime on corresponding
NETDEV_CHANGEADDR or NETDEV_CHANGENAME notifications.
ioctl(SIOCSIFHWADDR or SIOCSIFNAME) could be used to change the hardware/MAC
address or name of the local interface that our netpoll is attached to.
Whenever this happens, netdev notifier chain is called out with the
NETDEV_CHANGEADDR or NETDEV_CHANGENAME event message. We respond to that and
update the local_mac or dev_name field of the struct netpoll. This makes
sense anyway, but is especially required for dynamic netconsole because the
netpoll structure's internal members become user visible files when either
sysfs or configfs are used. So this helps us to keep up with the MAC
address/name changes and keep values in struct netpoll uptodate.
[ Note that ioctl(SIOCSIFADDR) to change IP address of interface at
runtime is not handled (to update local_ip of netpoll) on purpose --
some setups may set the local_ip to a private address, not necessary
the actual IP address of the sender host, as presently allowed. ]
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Cc: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 32 ++++++++++++++++++++++++++++++++
1 files changed, 32 insertions(+)
diff -puN drivers/net/netconsole.c~netconsole-introduce-netconsole_netdev_notifier drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-introduce-netconsole_netdev_notifier
+++ a/drivers/net/netconsole.c
@@ -80,6 +80,33 @@ static struct netconsole_target default_
},
};
+/* Handle network interface device notifications */
+static int netconsole_netdev_event(struct notifier_block *this,
+ unsigned long event,
+ void *ptr)
+{
+ struct net_device *dev = ptr;
+ struct netconsole_target *nt = &default_target;
+
+ if (nt->np.dev == dev) {
+ switch (event) {
+ case NETDEV_CHANGEADDR:
+ memcpy(nt->np.local_mac, dev->dev_addr, ETH_ALEN);
+ break;
+
+ case NETDEV_CHANGENAME:
+ strlcpy(nt->np.dev_name, dev->name, IFNAMSIZ);
+ break;
+ }
+ }
+
+ return NOTIFY_DONE;
+}
+
+static struct notifier_block netconsole_netdev_notifier = {
+ .notifier_call = netconsole_netdev_event,
+};
+
static void write_msg(struct console *con, const char *msg, unsigned int len)
{
int frag, left;
@@ -122,6 +149,10 @@ static int __init init_netconsole(void)
if (err)
goto out;
+ err = register_netdevice_notifier(&netconsole_netdev_notifier);
+ if (err)
+ goto out;
+
register_console(&netconsole);
printk(KERN_INFO "netconsole: network logging started\n");
@@ -134,6 +165,7 @@ static void __exit cleanup_netconsole(vo
struct netconsole_target *nt = &default_target;
unregister_console(&netconsole);
+ unregister_netdevice_notifier(&netconsole_netdev_notifier);
netpoll_cleanup(&nt->np);
}
_
^ permalink raw reply
* [patch 21/28] netconsole: Use netif_running() in write_msg()
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
Avoid unnecessarily disabling interrupts and calling netpoll_send_udp() if the
corresponding local interface is not up.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Acked-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Cc: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 18 +++++++++---------
1 files changed, 9 insertions(+), 9 deletions(-)
diff -puN drivers/net/netconsole.c~netconsole-use-netif_running-in-write_msg drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-use-netif_running-in-write_msg
+++ a/drivers/net/netconsole.c
@@ -75,16 +75,16 @@ static void write_msg(struct console *co
int frag, left;
unsigned long flags;
- local_irq_save(flags);
-
- for (left = len; left;) {
- frag = min(left, MAX_PRINT_CHUNK);
- netpoll_send_udp(&np, msg, frag);
- msg += frag;
- left -= frag;
+ if (netif_running(np.dev)) {
+ local_irq_save(flags);
+ for (left = len; left;) {
+ frag = min(left, MAX_PRINT_CHUNK);
+ netpoll_send_udp(&np, msg, frag);
+ msg += frag;
+ left -= frag;
+ }
+ local_irq_restore(flags);
}
-
- local_irq_restore(flags);
}
static struct console netconsole = {
_
^ permalink raw reply
* [patch 16/18] net/tulip/xircom_cb.c: remove superfulous priv assignment
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, m.kozlowski, arjan
From: Mariusz Kozlowski <m.kozlowski@tuxland.pl>
It does
dev = alloc_etherdev(...
private = netdev_priv(dev);
...
dev->priv = private;
which doesn't make much sense (does it?) because this is done in
alloc_netdev() already.
struct net_device *alloc_netdev(...
{
...
if (sizeof_priv)
dev->priv = netdev_priv(dev);
This patch removes superfluous code.
Signed-off-by: Mariusz Kozlowski <m.kozlowski@tuxland.pl>
Acked-by: Arjan van de Ven <arjan@linux.intel.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/tulip/xircom_cb.c | 1 -
1 files changed, 1 deletion(-)
diff -puN drivers/net/tulip/xircom_cb.c~net-tulip-xircom_cbc-remove-superfulous-priv-assignment drivers/net/tulip/xircom_cb.c
--- a/drivers/net/tulip/xircom_cb.c~net-tulip-xircom_cbc-remove-superfulous-priv-assignment
+++ a/drivers/net/tulip/xircom_cb.c
@@ -271,7 +271,6 @@ static int __devinit xircom_probe(struct
dev->hard_start_xmit = &xircom_start_xmit;
dev->stop = &xircom_close;
dev->get_stats = &xircom_get_stats;
- dev->priv = private;
#ifdef CONFIG_NET_POLL_CONTROLLER
dev->poll_controller = &xircom_poll_controller;
#endif
_
^ permalink raw reply
* [patch 22/28] netconsole: Add some useful tips to documentation
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
Add some useful general-purpose tips. Also suggest solution for the frequent
problem of console loglevel set too low numerically (i.e. for high priority
messages only) on the sender.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Acked-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Acked-by: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
Documentation/networking/netconsole.txt | 25 ++++++++++++++++++++++
1 files changed, 25 insertions(+)
diff -puN Documentation/networking/netconsole.txt~netconsole-add-some-useful-tips-to-documentation Documentation/networking/netconsole.txt
--- a/Documentation/networking/netconsole.txt~netconsole-add-some-useful-tips-to-documentation
+++ a/Documentation/networking/netconsole.txt
@@ -44,11 +44,36 @@ WARNING: the default target ethernet set
ethernet address to send packets, which can cause increased load on
other systems on the same ethernet segment.
+TIP: some LAN switches may be configured to suppress ethernet broadcasts
+so it is advised to explicitly specify the remote agents' MAC addresses
+from the config parameters passed to netconsole.
+
+TIP: to find out the MAC address of, say, 10.0.0.2, you may try using:
+
+ ping -c 1 10.0.0.2 ; /sbin/arp -n | grep 10.0.0.2
+
+TIP: in case the remote logging agent is on a separate LAN subnet than
+the sender, it is suggested to try specifying the MAC address of the
+default gateway (you may use /sbin/route -n to find it out) as the
+remote MAC address instead.
+
NOTE: the network device (eth1 in the above case) can run any kind
of other network traffic, netconsole is not intrusive. Netconsole
might cause slight delays in other traffic if the volume of kernel
messages is high, but should have no other impact.
+NOTE: if you find that the remote logging agent is not receiving or
+printing all messages from the sender, it is likely that you have set
+the "console_loglevel" parameter (on the sender) to only send high
+priority messages to the console. You can change this at runtime using:
+
+ dmesg -n 8
+
+or by specifying "debug" on the kernel command line at boot, to send
+all kernel messages to the console. A specific value for this parameter
+can also be set using the "loglevel" kernel boot option. See the
+dmesg(8) man page and Documentation/kernel-parameters.txt for details.
+
Netconsole was designed to be as instantaneous as possible, to
enable the logging of even the most critical kernel bugs. It works
from IRQ contexts as well, and does not enable interrupts while
_
^ permalink raw reply
* [patch 11/18] drivers/net/cxgb3/xgmac.c: remove dead code
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, bunk
From: Adrian Bunk <bunk@stusta.de>
This patch removes dead code ("tx_xcnt" can never be != 0 at this place)
spotted by the Coverity checker.
Signed-off-by: Adrian Bunk <bunk@stusta.de>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/cxgb3/xgmac.c | 5 +----
1 files changed, 1 insertion(+), 4 deletions(-)
diff -puN drivers/net/cxgb3/xgmac.c~drivers-net-cxgb3-xgmacc-remove-dead-code drivers/net/cxgb3/xgmac.c
--- a/drivers/net/cxgb3/xgmac.c~drivers-net-cxgb3-xgmacc-remove-dead-code
+++ a/drivers/net/cxgb3/xgmac.c
@@ -524,10 +524,7 @@ int t3b2_mac_watchdog_task(struct cmac *
goto rxcheck;
}
- if (((tx_tcnt != mac->tx_tcnt) &&
- (tx_xcnt == 0) && (mac->tx_xcnt == 0)) ||
- ((mac->tx_mcnt == tx_mcnt) &&
- (tx_xcnt != 0) && (mac->tx_xcnt != 0))) {
+ if ((tx_tcnt != mac->tx_tcnt) && (mac->tx_xcnt == 0)) {
if (mac->toggle_cnt > 4) {
status = 2;
goto out;
_
^ permalink raw reply
* [patch 18/18] 3c59x maintainer
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, klassert
From: Steffen Klassert <klassert@mathematik.tu-chemnitz.de>
Add 3c59x maintainer.
Signed-off-by: Steffen Klassert <klassert@mathematik.tu-chemnitz.de>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
MAINTAINERS | 6 ++++++
1 files changed, 6 insertions(+)
diff -puN MAINTAINERS~add-3c59x-maintainer MAINTAINERS
--- a/MAINTAINERS~add-3c59x-maintainer
+++ a/MAINTAINERS
@@ -97,6 +97,12 @@ M: philb@gnu.org
L: netdev@vger.kernel.org
S: Maintained
+3C59X NETWORK DRIVER
+P: Steffen Klassert
+M: klassert@mathematik.tu-chemnitz.de
+L: netdev@vger.kernel.org
+S: Maintained
+
3CR990 NETWORK DRIVER
P: David Dillow
M: dave@thedillows.org
_
^ permalink raw reply
* [patch 15/18] drivers/net: remove superfluous memset
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm, m.kozlowski
From: Mariusz Kozlowski <m.kozlowski@tuxland.pl>
This patch covers something like this:
dev = alloc_*dev(...
...
priv = netdev_priv(dev);
memset(priv, 0, sizeof(*priv));
The memset() here is superfluous. alloc_netdev() uses kzalloc()
to allocate needed memory so there is no need to zero the priv region
twice.
Signed-off-by: Mariusz Kozlowski <m.kozlowski@tuxland.pl>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/fs_enet/fs_enet-main.c | 1 -
drivers/net/myri10ge/myri10ge.c | 1 -
drivers/net/netxen/netxen_nic_main.c | 1 -
drivers/net/sunlance.c | 1 -
drivers/net/usb/pegasus.c | 1 -
drivers/net/usb/rtl8150.c | 1 -
6 files changed, 6 deletions(-)
diff -puN drivers/net/fs_enet/fs_enet-main.c~drivers-net-remove-superfluous-memset drivers/net/fs_enet/fs_enet-main.c
--- a/drivers/net/fs_enet/fs_enet-main.c~drivers-net-remove-superfluous-memset
+++ a/drivers/net/fs_enet/fs_enet-main.c
@@ -962,7 +962,6 @@ static struct net_device *fs_init_instan
SET_MODULE_OWNER(ndev);
fep = netdev_priv(ndev);
- memset(fep, 0, privsize); /* clear everything */
fep->dev = dev;
dev_set_drvdata(dev, ndev);
diff -puN drivers/net/myri10ge/myri10ge.c~drivers-net-remove-superfluous-memset drivers/net/myri10ge/myri10ge.c
--- a/drivers/net/myri10ge/myri10ge.c~drivers-net-remove-superfluous-memset
+++ a/drivers/net/myri10ge/myri10ge.c
@@ -2852,7 +2852,6 @@ static int myri10ge_probe(struct pci_dev
SET_NETDEV_DEV(netdev, &pdev->dev);
mgp = netdev_priv(netdev);
- memset(mgp, 0, sizeof(*mgp));
mgp->dev = netdev;
mgp->pdev = pdev;
mgp->csum_flag = MXGEFW_FLAGS_CKSUM;
diff -puN drivers/net/netxen/netxen_nic_main.c~drivers-net-remove-superfluous-memset drivers/net/netxen/netxen_nic_main.c
--- a/drivers/net/netxen/netxen_nic_main.c~drivers-net-remove-superfluous-memset
+++ a/drivers/net/netxen/netxen_nic_main.c
@@ -329,7 +329,6 @@ netxen_nic_probe(struct pci_dev *pdev, c
SET_NETDEV_DEV(netdev, &pdev->dev);
adapter = netdev->priv;
- memset(adapter, 0 , sizeof(struct netxen_adapter));
adapter->ahw.pdev = pdev;
adapter->ahw.pci_func = pci_func_id;
diff -puN drivers/net/sunlance.c~drivers-net-remove-superfluous-memset drivers/net/sunlance.c
--- a/drivers/net/sunlance.c~drivers-net-remove-superfluous-memset
+++ a/drivers/net/sunlance.c
@@ -1335,7 +1335,6 @@ static int __devinit sparc_lance_probe_o
return -ENOMEM;
lp = netdev_priv(dev);
- memset(lp, 0, sizeof(*lp));
if (sparc_lance_debug && version_printed++ == 0)
printk (KERN_INFO "%s", version);
diff -puN drivers/net/usb/pegasus.c~drivers-net-remove-superfluous-memset drivers/net/usb/pegasus.c
--- a/drivers/net/usb/pegasus.c~drivers-net-remove-superfluous-memset
+++ a/drivers/net/usb/pegasus.c
@@ -1306,7 +1306,6 @@ static int pegasus_probe(struct usb_inte
}
pegasus = netdev_priv(net);
- memset(pegasus, 0, sizeof (struct pegasus));
pegasus->dev_index = dev_index;
init_waitqueue_head(&pegasus->ctrl_wait);
diff -puN drivers/net/usb/rtl8150.c~drivers-net-remove-superfluous-memset drivers/net/usb/rtl8150.c
--- a/drivers/net/usb/rtl8150.c~drivers-net-remove-superfluous-memset
+++ a/drivers/net/usb/rtl8150.c
@@ -905,7 +905,6 @@ static int rtl8150_probe(struct usb_inte
}
dev = netdev_priv(netdev);
- memset(dev, 0, sizeof(rtl8150_t));
dev->intr_buff = kmalloc(INTBUFSIZE, GFP_KERNEL);
if (!dev->intr_buff) {
_
^ permalink raw reply
* [patch 27/28] Introduce U16_MAX and U32_MAX
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam
From: Satyam Sharma <satyam@infradead.org>
... in kernel.h and clean up home-grown macros elsewhere in the tree.
Leave out the one in reiserfs_fs.h as it is in the userspace-visible part
of that header. Still, #undef the (equivalent) kernel version there to
avoid seeing "redefined, previous definition was here" gcc warnings.
[akpm@linux-foundation.org: fix U16_MAX, U32_MAX defns]
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 7 +++----
include/linux/kernel.h | 3 +++
include/linux/reiserfs_fs.h | 1 +
net/ipv4/tcp_illinois.c | 2 +-
4 files changed, 8 insertions(+), 5 deletions(-)
diff -puN drivers/net/netconsole.c~introduce-u16_max-and-u32_max drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~introduce-u16_max-and-u32_max
+++ a/drivers/net/netconsole.c
@@ -34,6 +34,7 @@
*
****************************************************************/
+#include <linux/kernel.h>
#include <linux/mm.h>
#include <linux/init.h>
#include <linux/module.h>
@@ -389,7 +390,6 @@ static ssize_t store_local_port(struct n
size_t count)
{
long local_port;
-#define __U16_MAX ((__u16) ~0U)
if (nt->enabled) {
printk(KERN_ERR "netconsole: target (%s) is enabled, "
@@ -398,7 +398,7 @@ static ssize_t store_local_port(struct n
return -EINVAL;
}
- local_port = strtol10_check_range(buf, 0, __U16_MAX);
+ local_port = strtol10_check_range(buf, 0, U16_MAX);
if (local_port < 0)
return local_port;
@@ -412,7 +412,6 @@ static ssize_t store_remote_port(struct
size_t count)
{
long remote_port;
-#define __U16_MAX ((__u16) ~0U)
if (nt->enabled) {
printk(KERN_ERR "netconsole: target (%s) is enabled, "
@@ -421,7 +420,7 @@ static ssize_t store_remote_port(struct
return -EINVAL;
}
- remote_port = strtol10_check_range(buf, 0, __U16_MAX);
+ remote_port = strtol10_check_range(buf, 0, U16_MAX);
if (remote_port < 0)
return remote_port;
diff -puN include/linux/kernel.h~introduce-u16_max-and-u32_max include/linux/kernel.h
--- a/include/linux/kernel.h~introduce-u16_max-and-u32_max
+++ a/include/linux/kernel.h
@@ -30,6 +30,9 @@ extern const char linux_proc_banner[];
#define LLONG_MIN (-LLONG_MAX - 1)
#define ULLONG_MAX (~0ULL)
+#define U16_MAX (0xffff)
+#define U32_MAX (0xffffffff)
+
#define STACK_MAGIC 0xdeadbeef
#define ALIGN(x,a) __ALIGN_MASK(x,(typeof(x))(a)-1)
diff -puN include/linux/reiserfs_fs.h~introduce-u16_max-and-u32_max include/linux/reiserfs_fs.h
--- a/include/linux/reiserfs_fs.h~introduce-u16_max-and-u32_max
+++ a/include/linux/reiserfs_fs.h
@@ -1225,6 +1225,7 @@ struct treepath var = {.path_length = IL
#define MAX_US_INT 0xffff
// reiserfs version 2 has max offset 60 bits. Version 1 - 32 bit offset
+#undef U32_MAX
#define U32_MAX (~(__u32)0)
static inline loff_t max_reiserfs_offset(struct inode *inode)
diff -puN net/ipv4/tcp_illinois.c~introduce-u16_max-and-u32_max net/ipv4/tcp_illinois.c
--- a/net/ipv4/tcp_illinois.c~introduce-u16_max-and-u32_max
+++ a/net/ipv4/tcp_illinois.c
@@ -12,6 +12,7 @@
* Copyright (C) 2007 Stephen Hemminger <shemminger@linux-foundation.org>
*/
+#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/skbuff.h>
#include <linux/inet_diag.h>
@@ -23,7 +24,6 @@
#define ALPHA_MIN ((3*ALPHA_SCALE)/10) /* ~0.3 */
#define ALPHA_MAX (10*ALPHA_SCALE) /* 10.0 */
#define ALPHA_BASE ALPHA_SCALE /* 1.0 */
-#define U32_MAX ((u32)~0U)
#define RTT_MAX (U32_MAX / ALPHA_MAX) /* 3.3 secs */
#define BETA_SHIFT 6
_
^ permalink raw reply
* [patch 28/28] Introduce strtol_check_range()
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam
From: Satyam Sharma <satyam@infradead.org>
Callers (especially "store" functions for sysfs or configfs attributes)
that want to convert an input string to a number may often also want to
check for simple input sanity or allowable range. strtol10_check_range()
of netconsole does this, so extract it out into lib/vsprintf.c, make it
generic w.r.t. base, and export it to the rest of the kernel and modules.
[akpm@linux-foundation.org: cleanups]
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 46 +++++++++----------------------------
include/linux/kernel.h | 2 +
lib/vsprintf.c | 29 +++++++++++++++++++++++
3 files changed, 43 insertions(+), 34 deletions(-)
diff -puN drivers/net/netconsole.c~introduce-strtol_check_range drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~introduce-strtol_check_range
+++ a/drivers/net/netconsole.c
@@ -242,34 +242,6 @@ static struct netconsole_target *to_targ
}
/*
- * Wrapper over simple_strtol (base 10) with sanity and range checking.
- * We return (signed) long only because we may want to return errors.
- * Do not use this to convert numbers that are allowed to be negative.
- */
-static long strtol10_check_range(const char *cp, long min, long max)
-{
- long ret;
- char *p = (char *) cp;
-
- WARN_ON(min < 0);
- WARN_ON(max < min);
-
- ret = simple_strtol(p, &p, 10);
-
- if (*p && (*p != '\n')) {
- printk(KERN_ERR "netconsole: invalid input\n");
- return -EINVAL;
- }
- if ((ret < min) || (ret > max)) {
- printk(KERN_ERR "netconsole: input %ld must be between "
- "%ld and %ld\n", ret, min, max);
- return -EINVAL;
- }
-
- return ret;
-}
-
-/*
* Attribute operations for netconsole_target.
*/
@@ -335,9 +307,11 @@ static ssize_t store_enabled(struct netc
int err;
long enabled;
- enabled = strtol10_check_range(buf, 0, 1);
- if (enabled < 0)
+ enabled = strtol_check_range(buf, 0, 1, 10);
+ if (enabled < 0) {
+ printk(KERN_ERR "netconsole: invalid input\n");
return enabled;
+ }
if (enabled) { /* 1 */
@@ -398,9 +372,11 @@ static ssize_t store_local_port(struct n
return -EINVAL;
}
- local_port = strtol10_check_range(buf, 0, U16_MAX);
- if (local_port < 0)
+ local_port = strtol_check_range(buf, 0, U16_MAX, 10);
+ if (local_port < 0) {
+ printk(KERN_ERR "netconsole: invalid input\n");
return local_port;
+ }
nt->np.local_port = local_port;
@@ -420,9 +396,11 @@ static ssize_t store_remote_port(struct
return -EINVAL;
}
- remote_port = strtol10_check_range(buf, 0, U16_MAX);
- if (remote_port < 0)
+ remote_port = strtol_check_range(buf, 0, U16_MAX, 10);
+ if (remote_port < 0) {
+ printk(KERN_ERR "netconsole: invalid input\n");
return remote_port;
+ }
nt->np.remote_port = remote_port;
diff -puN include/linux/kernel.h~introduce-strtol_check_range include/linux/kernel.h
--- a/include/linux/kernel.h~introduce-strtol_check_range
+++ a/include/linux/kernel.h
@@ -121,6 +121,8 @@ extern unsigned long simple_strtoul(cons
extern long simple_strtol(const char *,char **,unsigned int);
extern unsigned long long simple_strtoull(const char *,char **,unsigned int);
extern long long simple_strtoll(const char *,char **,unsigned int);
+extern long strtol_check_range(const char *cp, long min, long max,
+ unsigned int base);
extern int sprintf(char * buf, const char * fmt, ...)
__attribute__ ((format (printf, 2, 3)));
extern int vsprintf(char *buf, const char *, va_list)
diff -puN lib/vsprintf.c~introduce-strtol_check_range lib/vsprintf.c
--- a/lib/vsprintf.c~introduce-strtol_check_range
+++ a/lib/vsprintf.c
@@ -126,6 +126,35 @@ long long simple_strtoll(const char *cp,
return simple_strtoull(cp,endp,base);
}
+/**
+ * strtol_check_range - wrapper over simple_strtol with input and range checking
+ * @cp: The start of the string
+ * @min: Minimum value allowed
+ * @max: Maximum value allowed
+ * @base: The number base to use
+ *
+ * We return (signed) long only because we may want to return errors.
+ * Do not use this to convert numbers that are allowed to be negative.
+ */
+long strtol_check_range(const char *cp, long min, long max, unsigned int base)
+{
+ long ret;
+ char *p = (char *) cp;
+
+ WARN_ON(min < 0);
+ WARN_ON(max < min);
+
+ ret = simple_strtol(p, &p, base);
+
+ if (*p && (*p != '\n'))
+ return -EINVAL;
+ if ((ret < min) || (ret > max))
+ return -EINVAL;
+
+ return ret;
+}
+EXPORT_SYMBOL(strtol_check_range);
+
static int skip_atoi(const char **s)
{
int i=0;
_
^ permalink raw reply
* [patch 10/18] ax88796 printk fixes
From: akpm @ 2007-08-10 21:05 UTC (permalink / raw)
To: jeff; +Cc: netdev, akpm
From: Andrew Morton <akpm@linux-foundation.org>
drivers/net/ax88796.c: In function `ax_probe':
drivers/net/ax88796.c:825: warning: size_t format, different type arg (arg 4)
drivers/net/ax88796.c:825: warning: size_t format, different type arg (arg 5)
resource_size_t isn't size_t.
Cc: Jeff Garzik <jeff@garzik.org>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/ax88796.c | 5 +++--
1 files changed, 3 insertions(+), 2 deletions(-)
diff -puN drivers/net/ax88796.c~ax88796-printk-fixes drivers/net/ax88796.c
--- a/drivers/net/ax88796.c~ax88796-printk-fixes
+++ a/drivers/net/ax88796.c
@@ -821,8 +821,9 @@ static int ax_probe(struct platform_devi
dev->base_addr = (unsigned long)ei_status.mem;
if (ei_status.mem == NULL) {
- dev_err(&pdev->dev, "Cannot ioremap area (%08zx,%08zx)\n",
- res->start, res->end);
+ dev_err(&pdev->dev, "Cannot ioremap area (%08llx,%08llx)\n",
+ (unsigned long long)res->start,
+ (unsigned long long)res->end);
ret = -ENXIO;
goto exit_req;
_
^ permalink raw reply
* Re: [patch 03/18] drivers/net/ns83820.c: add paramter to disable autonegotiation
From: Benjamin LaHaise @ 2007-08-10 21:13 UTC (permalink / raw)
To: akpm; +Cc: jeff, netdev, dan, dan, jgarzik
In-Reply-To: <200708102105.l7AL5ERH008951@imap1.linux-foundation.org>
On Fri, Aug 10, 2007 at 02:05:13PM -0700, akpm@linux-foundation.org wrote:
> Also added a "disable_autoneg" module argument to completely disable
> autoneg on all cards using this driver.
...
> [akpm: this is a previously-nacked patch, but the problem is real]
Please remove this part of the patch. The ethtool support is sufficient and
doesn't clobber other cards in the system. At the very least the module
parameter has to be limited to a specific card.
-ben
--
"Time is of no importance, Mr. President, only life is important."
Don't Email: <zyntrop@kvack.org>.
^ permalink raw reply
* [patch 02/28] ip_auto_config fix
From: akpm @ 2007-08-10 21:11 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, joakim.tjernlund, trond.myklebust
From: Joakim Tjernlund <joakim.tjernlund@transmode.se>
The following commandline:
root=/dev/mtdblock6 rw rootfstype=jffs2 ip=192.168.1.10:::255.255.255.0:localhost.localdomain:eth1:off console=ttyS0,115200
makes ip_auto_config fall back to DHCP and complain "IP-Config: Incomplete
network configuration information." depending on if CONFIG_IP_PNP_DHCP is
set or not.
The only way I can make ip_auto_config accept my IP config is to add an
entry for the server IP:
ip=192.168.1.10:192.168.1.15::255.255.255.0:localhost.localdomain:eth1:off
I think this is a bug since I am not using a NFS root FS.
The following patch fixes the above problem.
From: Andrew Morton <akpm@linux-foundation.org>
Davem said (in February!):
Well, first of all the change in question is not in 2.4.x either. I just
checked the current 2.4.x GIT tree and the test is exactly:
if (ic_myaddr == INADDR_NONE ||
#ifdef CONFIG_ROOT_NFS
(MAJOR(ROOT_DEV) == UNNAMED_MAJOR
&& root_server_addr == INADDR_NONE
&& ic_servaddr == INADDR_NONE) ||
#endif
ic_first_dev->next) {
which matches 2.6.x
I even checked 2.4.x when it was branched for 2.5.x and the test was the
same at the point in time too.
Looking at the proposed change a bit it appears that it is probably
correct, as it's trying to check that ROOT_DEV is nfs root. But if it is
correct then the UNNAMED_MAJOR comparison in the same code block should be
removed as it becomes superfluous.
I'm happy to apply this patch with that modification made.
Signed-off-by: Joakim Tjernlund <joakim.tjernlund@transmode.se>
Cc: "David S. Miller" <davem@davemloft.net>
Cc: Trond Myklebust <trond.myklebust@fys.uio.no>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
net/ipv4/ipconfig.c | 6 +++---
1 files changed, 3 insertions(+), 3 deletions(-)
diff -puN net/ipv4/ipconfig.c~ip_auto_config-fix net/ipv4/ipconfig.c
--- a/net/ipv4/ipconfig.c~ip_auto_config-fix
+++ a/net/ipv4/ipconfig.c
@@ -1281,9 +1281,9 @@ static int __init ip_auto_config(void)
*/
if (ic_myaddr == NONE ||
#ifdef CONFIG_ROOT_NFS
- (MAJOR(ROOT_DEV) == UNNAMED_MAJOR
- && root_server_addr == NONE
- && ic_servaddr == NONE) ||
+ (root_server_addr == NONE
+ && ic_servaddr == NONE
+ && ROOT_DEV == Root_NFS) ||
#endif
ic_first_dev->next) {
#ifdef IPCONFIG_DYNAMIC
_
^ permalink raw reply
* [patch 11/28] fix theoretical ccids_{read,write}_lock() race
From: akpm @ 2007-08-10 21:11 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, oleg, acme, mingo
From: Oleg Nesterov <oleg@tv-sign.ru>
Make sure that spin_unlock_wait() is properly ordered wrt atomic_inc().
(akpm: can't we convert this code to use rwlocks?)
Signed-off-by: Oleg Nesterov <oleg@tv-sign.ru>
Cc: Arnaldo Carvalho de Melo <acme@redhat.com>
Cc: Ingo Molnar <mingo@elte.hu>
Cc: "David S. Miller" <davem@davemloft.net>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
net/dccp/ccid.c | 1 +
1 files changed, 1 insertion(+)
diff -puN net/dccp/ccid.c~fix-theoretical-ccids_readwrite_lock-race net/dccp/ccid.c
--- a/net/dccp/ccid.c~fix-theoretical-ccids_readwrite_lock-race
+++ a/net/dccp/ccid.c
@@ -40,6 +40,7 @@ static inline void ccids_write_unlock(vo
static inline void ccids_read_lock(void)
{
atomic_inc(&ccids_lockct);
+ smp_mb__after_atomic_inc();
spin_unlock_wait(&ccids_lock);
}
_
^ permalink raw reply
* [patch 18/28] netconsole: Cleanups, codingstyle, prettyfication
From: akpm @ 2007-08-10 21:12 UTC (permalink / raw)
To: davem; +Cc: netdev, akpm, satyam, k-keiichi, mpm
From: Satyam Sharma <satyam@infradead.org>
Based upon initial work by Keiichi Kii <k-keiichi@bx.jp.nec.com>.
(1) Remove unwanted headers.
(2) Mark __init and __exit as appropriate.
(3) Various trivial codingstyle and prettification stuff.
Signed-off-by: Satyam Sharma <satyam@infradead.org>
Signed-off-by: Keiichi Kii <k-keiichi@bx.jp.nec.com>
Acked-by: Matt Mackall <mpm@selenic.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
---
drivers/net/netconsole.c | 55 ++++++++++++++++++-------------------
1 files changed, 27 insertions(+), 28 deletions(-)
diff -puN drivers/net/netconsole.c~netconsole-cleanups-codingstyle-prettyfication drivers/net/netconsole.c
--- a/drivers/net/netconsole.c~netconsole-cleanups-codingstyle-prettyfication
+++ a/drivers/net/netconsole.c
@@ -35,35 +35,32 @@
****************************************************************/
#include <linux/mm.h>
-#include <linux/tty.h>
#include <linux/init.h>
#include <linux/module.h>
#include <linux/console.h>
-#include <linux/tty_driver.h>
#include <linux/moduleparam.h>
#include <linux/string.h>
-#include <linux/sysrq.h>
-#include <linux/smp.h>
#include <linux/netpoll.h>
MODULE_AUTHOR("Maintainer: Matt Mackall <mpm@selenic.com>");
MODULE_DESCRIPTION("Console driver for network interfaces");
MODULE_LICENSE("GPL");
-static char config[256];
-module_param_string(netconsole, config, 256, 0);
+#define MAX_PARAM_LENGTH 256
+#define MAX_PRINT_CHUNK 1000
+
+static char config[MAX_PARAM_LENGTH];
+module_param_string(netconsole, config, MAX_PARAM_LENGTH, 0);
MODULE_PARM_DESC(netconsole, " netconsole=[src-port]@[src-ip]/[dev],[tgt-port]@<tgt-ip>/[tgt-macaddr]\n");
static struct netpoll np = {
- .name = "netconsole",
- .dev_name = "eth0",
- .local_port = 6665,
- .remote_port = 6666,
- .remote_mac = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
+ .name = "netconsole",
+ .dev_name = "eth0",
+ .local_port = 6665,
+ .remote_port = 6666,
+ .remote_mac = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff},
};
-static int configured = 0;
-
-#define MAX_PRINT_CHUNK 1000
+static int configured;
static void write_msg(struct console *con, const char *msg, unsigned int len)
{
@@ -75,7 +72,7 @@ static void write_msg(struct console *co
local_irq_save(flags);
- for(left = len; left; ) {
+ for (left = len; left;) {
frag = min(left, MAX_PRINT_CHUNK);
netpoll_send_udp(&np, msg, frag);
msg += frag;
@@ -86,12 +83,12 @@ static void write_msg(struct console *co
}
static struct console netconsole = {
- .name = "netcon",
- .flags = CON_ENABLED | CON_PRINTBUFFER,
- .write = write_msg
+ .name = "netcon",
+ .flags = CON_ENABLED | CON_PRINTBUFFER,
+ .write = write_msg,
};
-static int option_setup(char *opt)
+static int __init option_setup(char *opt)
{
configured = !netpoll_parse_options(&np, opt);
return 1;
@@ -99,28 +96,30 @@ static int option_setup(char *opt)
__setup("netconsole=", option_setup);
-static int init_netconsole(void)
+static int __init init_netconsole(void)
{
- int err;
+ int err = 0;
- if(strlen(config))
+ if (strnlen(config, MAX_PARAM_LENGTH))
option_setup(config);
- if(!configured) {
- printk("netconsole: not configured, aborting\n");
- return 0;
+ if (!configured) {
+ printk(KERN_INFO "netconsole: not configured, aborting\n");
+ goto out;
}
err = netpoll_setup(&np);
if (err)
- return err;
+ goto out;
register_console(&netconsole);
printk(KERN_INFO "netconsole: network logging started\n");
- return 0;
+
+out:
+ return err;
}
-static void cleanup_netconsole(void)
+static void __exit cleanup_netconsole(void)
{
unregister_console(&netconsole);
netpoll_cleanup(&np);
_
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox