#include <linux/fs.h>
#include <linux/string.h>
#include <linux/kernel.h>
+#include <linux/bug.h>
#if 0
#define DEBUGP printk
apply_paravirt(pseg, pseg + para->sh_size);
}
- return 0;
+ return module_bug_finalize(hdr, sechdrs, me);
}
void module_arch_cleanup(struct module *mod)
{
alternatives_smp_module_del(mod);
+ module_bug_cleanup(mod);
}
#include <linux/unwind.h>
#include <linux/uaccess.h>
#include <linux/nmi.h>
+#include <linux/bug.h>
#ifdef CONFIG_EISA
#include <linux/ioport.h>
printk("\n");
}
-static void handle_BUG(struct pt_regs *regs)
+int is_valid_bugaddr(unsigned long eip)
{
- unsigned long eip = regs->eip;
unsigned short ud2;
if (eip < PAGE_OFFSET)
- return;
+ return 0;
if (probe_kernel_address((unsigned short *)eip, ud2))
- return;
- if (ud2 != 0x0b0f)
- return;
-
- printk(KERN_EMERG "------------[ cut here ]------------\n");
-
-#ifdef CONFIG_DEBUG_BUGVERBOSE
- do {
- unsigned short line;
- char *file;
- char c;
-
- if (probe_kernel_address((unsigned short *)(eip + 2), line))
- break;
- if (probe_kernel_address((char **)(eip + 4), file) ||
- (unsigned long)file < PAGE_OFFSET ||
- probe_kernel_address(file, c))
- file = "<bad filename>";
+ return 0;
- printk(KERN_EMERG "kernel BUG at %s:%d!\n", file, line);
- return;
- } while (0);
-#endif
- printk(KERN_EMERG "Kernel BUG at [verbose debug info unavailable]\n");
+ return ud2 == 0x0b0f;
}
-/* This is gone through when something in the kernel
- * has done something bad and is about to be terminated.
-*/
+/*
+ * This is gone through when something in the kernel has done something bad and
+ * is about to be terminated.
+ */
void die(const char * str, struct pt_regs * regs, long err)
{
static struct {
unsigned long esp;
unsigned short ss;
- handle_BUG(regs);
+ report_bug(regs->eip);
+
printk(KERN_EMERG "%s: %04lx [#%d]\n", str, err & 0xffff, ++die_counter);
#ifdef CONFIG_PREEMPT
printk(KERN_EMERG "PREEMPT ");
/*
* Tell the user there is some problem.
- * The offending file and line are encoded after the "officially
- * undefined" opcode for parsing in the trap handler.
+ * The offending file and line are encoded encoded in the __bug_table section.
*/
#ifdef CONFIG_BUG
#define HAVE_ARCH_BUG
+
#ifdef CONFIG_DEBUG_BUGVERBOSE
-#define BUG() \
- __asm__ __volatile__( "ud2\n" \
- "\t.word %c0\n" \
- "\t.long %c1\n" \
- : : "i" (__LINE__), "i" (__FILE__))
+#define BUG() \
+ do { \
+ asm volatile("1:\tud2\n" \
+ ".pushsection __bug_table,\"a\"\n" \
+ "2:\t.long 1b, %c0\n" \
+ "\t.word %c1, 0\n" \
+ "\t.org 2b+%c2\n" \
+ ".popsection" \
+ : : "i" (__FILE__), "i" (__LINE__), \
+ "i" (sizeof(struct bug_entry))); \
+ for(;;) ; \
+ } while(0)
+
#else
-#define BUG() __asm__ __volatile__("ud2\n")
+#define BUG() \
+ do { \
+ asm volatile("ud2"); \
+ for(;;) ; \
+ } while(0)
#endif
#endif
config DEBUG_BUGVERBOSE
bool "Verbose BUG() reporting (adds 70K)" if DEBUG_KERNEL && EMBEDDED
depends on BUG
- depends on ARM || ARM26 || AVR32 || M32R || M68K || SPARC32 || SPARC64 || X86_32 || FRV || SUPERH || GENERIC_BUG
+ depends on ARM || ARM26 || AVR32 || M32R || M68K || SPARC32 || SPARC64 || FRV || SUPERH || GENERIC_BUG
default !EMBEDDED
help
Say Y here to make BUG() panics output the file name and line number