diff options
author | Ian S. Nelson <nelsonian@comcast.net> | 2006-09-29 02:01:31 -0700 |
---|---|---|
committer | Linus Torvalds <torvalds@g5.osdl.org> | 2006-09-29 09:18:23 -0700 |
commit | 04b1db9fd7eea63c9663072feece616ea41b0a79 (patch) | |
tree | 70b92bf4040acbad744970b82432caac768c2658 | |
parent | 3b5e0cbb4fb6e2a599d72652f56a9acb6af16bcf (diff) |
[PATCH] /sys/modules: allow full length section names
I've been using systemtap for some debugging and I noticed that it can't
probe a lot of modules. Turns out it's kind of silly, the sections section
of /sys/module is limited to 32byte filenames and many of the actual
sections are a a bit longer than that.
[akpm@osdl.org: rewrite to use dymanic allocation]
Cc: Rusty Russell <rusty@rustcorp.com.au>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
-rw-r--r-- | CREDITS | 3 | ||||
-rw-r--r-- | include/linux/module.h | 4 | ||||
-rw-r--r-- | kernel/module.c | 26 |
3 files changed, 24 insertions, 9 deletions
@@ -2478,7 +2478,8 @@ S: Derbyshire DE4 3RL S: United Kingdom N: Ian S. Nelson -E: ian.nelson@echostar.com +E: nelsonis@earthlink.net +P: 1024D/00D3D983 3EFD 7B86 B888 D7E2 29B6 9E97 576F 1B97 00D3 D983 D: Minor mmap and ide hacks S: 1370 Atlantis Ave. S: Lafayette CO, 80026 diff --git a/include/linux/module.h b/include/linux/module.h index d4486cc2e7fe..2c599175c583 100644 --- a/include/linux/module.h +++ b/include/linux/module.h @@ -232,17 +232,17 @@ enum module_state }; /* Similar stuff for section attributes. */ -#define MODULE_SECT_NAME_LEN 32 struct module_sect_attr { struct module_attribute mattr; - char name[MODULE_SECT_NAME_LEN]; + char *name; unsigned long address; }; struct module_sect_attrs { struct attribute_group grp; + int nsections; struct module_sect_attr attrs[0]; }; diff --git a/kernel/module.c b/kernel/module.c index b7fe6e840963..05625d5dc758 100644 --- a/kernel/module.c +++ b/kernel/module.c @@ -933,6 +933,15 @@ static ssize_t module_sect_show(struct module_attribute *mattr, return sprintf(buf, "0x%lx\n", sattr->address); } +static void free_sect_attrs(struct module_sect_attrs *sect_attrs) +{ + int section; + + for (section = 0; section < sect_attrs->nsections; section++) + kfree(sect_attrs->attrs[section].name); + kfree(sect_attrs); +} + static void add_sect_attrs(struct module *mod, unsigned int nsect, char *secstrings, Elf_Shdr *sechdrs) { @@ -949,21 +958,26 @@ static void add_sect_attrs(struct module *mod, unsigned int nsect, + nloaded * sizeof(sect_attrs->attrs[0]), sizeof(sect_attrs->grp.attrs[0])); size[1] = (nloaded + 1) * sizeof(sect_attrs->grp.attrs[0]); - if (! (sect_attrs = kmalloc(size[0] + size[1], GFP_KERNEL))) + sect_attrs = kzalloc(size[0] + size[1], GFP_KERNEL); + if (sect_attrs == NULL) return; /* Setup section attributes. */ sect_attrs->grp.name = "sections"; sect_attrs->grp.attrs = (void *)sect_attrs + size[0]; + sect_attrs->nsections = 0; sattr = §_attrs->attrs[0]; gattr = §_attrs->grp.attrs[0]; for (i = 0; i < nsect; i++) { if (! (sechdrs[i].sh_flags & SHF_ALLOC)) continue; sattr->address = sechdrs[i].sh_addr; - strlcpy(sattr->name, secstrings + sechdrs[i].sh_name, - MODULE_SECT_NAME_LEN); + sattr->name = kstrdup(secstrings + sechdrs[i].sh_name, + GFP_KERNEL); + if (sattr->name == NULL) + goto out; + sect_attrs->nsections++; sattr->mattr.show = module_sect_show; sattr->mattr.store = NULL; sattr->mattr.attr.name = sattr->name; @@ -979,7 +993,7 @@ static void add_sect_attrs(struct module *mod, unsigned int nsect, mod->sect_attrs = sect_attrs; return; out: - kfree(sect_attrs); + free_sect_attrs(sect_attrs); } static void remove_sect_attrs(struct module *mod) @@ -989,13 +1003,13 @@ static void remove_sect_attrs(struct module *mod) &mod->sect_attrs->grp); /* We are positive that no one is using any sect attrs * at this point. Deallocate immediately. */ - kfree(mod->sect_attrs); + free_sect_attrs(mod->sect_attrs); mod->sect_attrs = NULL; } } - #else + static inline void add_sect_attrs(struct module *mod, unsigned int nsect, char *sectstrings, Elf_Shdr *sechdrs) { |