Module Name: src
Committed By: darran
Date: Mon May 3 09:51:36 UTC 2010
Modified Files:
src/sys/kern: kern_ctf.c kern_ksyms.c
Log Message:
DTrace: Fix several bugs where the mod_ctf_get() function could return
success even though no CTF section was present in the kernel or module.
This fixes the panic that several people saw when trying out the FBT
provider without updating /boot or missing a CTF section in /netbsd.
To generate a diff of this commit:
cvs rdiff -u -r1.2 -r1.3 src/sys/kern/kern_ctf.c
cvs rdiff -u -r1.58 -r1.59 src/sys/kern/kern_ksyms.c
Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.
Modified files:
Index: src/sys/kern/kern_ctf.c
diff -u src/sys/kern/kern_ctf.c:1.2 src/sys/kern/kern_ctf.c:1.3
--- src/sys/kern/kern_ctf.c:1.2 Sat Mar 13 01:41:14 2010
+++ src/sys/kern/kern_ctf.c Mon May 3 09:51:36 2010
@@ -1,4 +1,4 @@
-/* $NetBSD: kern_ctf.c,v 1.2 2010/03/13 01:41:14 christos Exp $ */
+/* $NetBSD: kern_ctf.c,v 1.3 2010/05/03 09:51:36 darran Exp $ */
/*-
* Copyright (c) 2008 John Birrell <[email protected]>
* All rights reserved.
@@ -82,8 +82,9 @@
uint8_t *ctfaddr;
size_t ctfsize;
- if (mc == NULL)
+ if (mc == NULL) {
return EINVAL;
+ }
/* Set the defaults for no CTF present. That's not a crime! */
memset(mc, 0, sizeof(*mc));
@@ -116,8 +117,9 @@
mc->strcnt = 0; /* XXX TBD */
mc->nsym = st->sd_symsize / sizeof(Elf_Sym);
} else {
- if (kobj_find_section(mod->mod_kobj, ".SUNW_ctf", (void **)&ctfaddr, &ctfsize))
+ if (kobj_find_section(mod->mod_kobj, ".SUNW_ctf", (void **)&ctfaddr, &ctfsize)) {
return ENOENT;
+ }
mc->symtab = mod->mod_kobj->ko_symtab;
mc->strtab = mod->mod_kobj->ko_strtab;
@@ -126,17 +128,21 @@
}
if (ctfaddr == NULL) {
+ error = ENOENT;
goto out;
}
/* Check the CTF magic number. (XXX check for big endian!) */
if (ctfaddr[0] != 0xf1 || ctfaddr[1] != 0xcf) {
+ error = EINVAL;
goto out;
}
/* Check if version 2. */
- if (ctfaddr[2] != 2)
+ if (ctfaddr[2] != 2) {
+ error = EINVAL;
goto out;
+ }
/* Check if the data is compressed. */
if ((ctfaddr[3] & 0x1) != 0) {
Index: src/sys/kern/kern_ksyms.c
diff -u src/sys/kern/kern_ksyms.c:1.58 src/sys/kern/kern_ksyms.c:1.59
--- src/sys/kern/kern_ksyms.c:1.58 Sun Mar 14 21:27:49 2010
+++ src/sys/kern/kern_ksyms.c Mon May 3 09:51:36 2010
@@ -1,4 +1,4 @@
-/* $NetBSD: kern_ksyms.c,v 1.58 2010/03/14 21:27:49 darran Exp $ */
+/* $NetBSD: kern_ksyms.c,v 1.59 2010/05/03 09:51:36 darran Exp $ */
/*-
* Copyright (c) 2008 The NetBSD Foundation, Inc.
@@ -71,7 +71,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kern_ksyms.c,v 1.58 2010/03/14 21:27:49 darran Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kern_ksyms.c,v 1.59 2010/05/03 09:51:36 darran Exp $");
#if defined(_KERNEL) && defined(_KERNEL_OPT)
#include "opt_ddb.h"
@@ -473,6 +473,9 @@
char *shstr = (uint8_t*)start +
shdr[ehdr->e_shstrndx].sh_offset;
for (i = 1; i < ehdr->e_shnum; i++) {
+#ifdef DEBUG
+ printf("ksyms: checking %s\n", &shstr[shdr[i].sh_name]);
+#endif
if (shdr[i].sh_type != SHT_PROGBITS)
continue;
if (strncmp(".SUNW_ctf", &shstr[shdr[i].sh_name] ,10) != 0)
@@ -486,6 +489,10 @@
#endif
break;
}
+#ifdef DEBUG
+ } else {
+ printf("ksyms: e_shstrndx == 0\n");
+#endif
}
#endif