Bug #7: Better breakpoints.
authorGustavo J. A. M. Carneiro <gjc@inescporto.pt>
Thu, 02 Aug 2007 13:59:08 +0100
changeset 1018 99476ef5580a
parent 1017 6f0bebab95c3
child 1019 5f7c8a0bd0fc
Bug #7: Better breakpoints.
src/core/assert.cc
src/core/assert.h
src/core/breakpoint.cc
src/core/breakpoint.h
src/core/fatal-error.h
src/core/uid-manager.cc
src/core/wscript
--- a/src/core/assert.cc	Thu Aug 02 08:55:56 2007 +0200
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,41 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * Copyright (c) 2006 INRIA
- * All rights reserved.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
- */
-
-#include "assert.h"
-
-namespace ns3 {
-
-void
-AssertBreakpoint (void)
-{
-  int *a = 0;
-  /**
-   * we test here to allow a debugger to change the value of
-   * the variable 'a' to allow the debugger to avoid the 
-   * subsequent segfault.
-   */
-  if (a == 0)
-    {
-      *a = 0;
-    }
-}
-
-}//namespace ns3
--- a/src/core/assert.h	Thu Aug 02 08:55:56 2007 +0200
+++ b/src/core/assert.h	Thu Aug 02 13:59:08 2007 +0100
@@ -21,36 +21,12 @@
 #ifndef ASSERT_H
 #define ASSERT_H
 
-/**
- * \defgroup assert Assert
- * \brief assert functions and macros
- *
- * The assert macros are used to verify
- * at runtime that a certain condition is true. If it is
- * not true, the program halts. These checks are built
- * into the program only in debugging builds. They are
- * removed in optimized builds.
- */
-
-namespace ns3 {
-
-/**
- * \ingroup debugging
- *
- * When an NS_ASSERT cannot verify its condition, 
- * this function is called. This is where you should
- * be able to put a breakpoint with a debugger if
- * you want to catch assertions before the program 
- * halts.
- */
-void AssertBreakpoint (void);
-
-}//namespace ns3
-
 #ifdef NS3_ASSERT_ENABLE
 
 #include <iostream>
 
+#include "breakpoint.h"
+
 /**
  * \ingroup assert
  * \param condition condition to verifiy.
@@ -68,7 +44,7 @@
           std::cerr << "assert failed. file=" << __FILE__ <<    \
             ", line=" << __LINE__ << ", cond=\""#condition <<   \
             "\"" << std::endl;                                  \
-          ns3::AssertBreakpoint ();                             \
+          NS_BREAKPOINT ();                                     \
         }                                                       \
     }                                                           \
   while (false)
@@ -89,7 +65,7 @@
       if (!(condition))                         \
         {                                       \
           std::cerr << message << std::endl;    \
-          ns3::AssertBreakpoint ();             \
+          NS_BREAKPOINT ();                     \
         }                                       \
     }                                           \
   while (false)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/core/breakpoint.cc	Thu Aug 02 13:59:08 2007 +0100
@@ -0,0 +1,58 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2006,2007 INRIA, INESC Porto
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
+ * Author: Gustavo Carneiro <gjc@inescporto.pt>
+ */
+
+#include "breakpoint.h"
+#include "ns3/core-config.h"
+#ifdef HAVE_SIGNAL_H
+# include <signal.h>
+#endif
+
+namespace ns3 {
+
+#ifdef HAVE_SIGNAL_H
+
+void
+Breakpoint (void)
+{
+  raise (SIGTRAP);
+}
+
+#else
+
+void
+Breakpoint (void)
+{
+  int *a = 0;
+  /**
+   * we test here to allow a debugger to change the value of
+   * the variable 'a' to allow the debugger to avoid the 
+   * subsequent segfault.
+   */
+  if (a == 0)
+    {
+      *a = 0;
+    }
+}
+
+#endif // HAVE_SIGNAL_H
+
+}//namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/core/breakpoint.h	Thu Aug 02 13:59:08 2007 +0100
@@ -0,0 +1,76 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2006,2007 INESC Porto, INRIA
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Gustavo Carneiro <gjc@inescporto.pt>
+ * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
+ */
+#ifndef BREAKPOINT_H
+#define BREAKPOINT_H
+
+namespace ns3 {
+
+/* Hacker macro to place breakpoints for selected machines.
+ * Actual use is strongly discouraged of course ;)
+ * Copied from GLib 2.12.9.
+ * Copyright (C) 1995-1997  Peter Mattis, Spencer Kimball and Josh MacDonald
+ *
+ * Modified by the GLib Team and others 1997-2000.  See the AUTHORS
+ * file for a list of people on the GLib Team.  See the ChangeLog
+ * files for a list of changes.  These files are distributed with
+ * GLib at ftp://ftp.gtk.org/pub/gtk/. 
+ */
+
+/**
+ * \ingroup debugging
+ *
+ * Inserts a breakpoint instruction (or equivalent system call) into
+ * the code for selected machines.  When an NS_ASSERT cannot verify its condition, 
+ * this macro is used. Falls back to calling
+ * AssertBreakpoint() for architectures where breakpoint assembly
+ * instructions are not supported.
+ */
+#if (defined (__i386__) || defined (__amd64__) || defined (__x86_64__)) && defined (__GNUC__) && __GNUC__ >= 2
+#  define NS_BREAKPOINT() \
+   do{ __asm__ __volatile__ ("int $03"); }while(false)
+#elif defined (_MSC_VER) && defined (_M_IX86)
+#  define NS_BREAKPOINT() \
+   do{ __asm int 3h }while(false)
+#elif defined (__alpha__) && !defined(__osf__) && defined (__GNUC__) && __GNUC__ >= 2
+#  define NS_BREAKPOINT() \
+   do{ __asm__ __volatile__ ("bpt"); }while(false)
+#else	/* !__i386__ && !__alpha__ */
+#  define NS_BREAKPOINT()    ns3::BreakpointFallback ()
+#endif
+
+/**
+ * \brief fallback breakpoint function
+ *
+ * This function is used by the NS_BREAKPOINT() macro as a fallback
+ * for when breakpoint assembly instructions are not available.  It
+ * attempts to halt program execution either by a raising SIGTRAP, on
+ * unix systems, or by dereferencing a null pointer.
+ * 
+ * Normally you should not call this function directly.
+ */
+void BreakpointFallback (void);
+
+
+}//namespace ns3
+
+
+#endif /* BREAKPOINT_H */
--- a/src/core/fatal-error.h	Thu Aug 02 08:55:56 2007 +0200
+++ b/src/core/fatal-error.h	Thu Aug 02 13:59:08 2007 +0100
@@ -21,7 +21,7 @@
 #ifndef FATAL_ERROR_H
 #define FATAL_ERROR_H
 
-#include "assert.h"
+#include "breakpoint.h"
 #include <iostream>
 
 /**
@@ -32,7 +32,7 @@
  *
  * When this macro is hit at runtime, the user-specified 
  * error message is output and the program is halted by calling
- * the ns3::AssertBreakpoint function. This macro is enabled
+ * the NS_DEBUG_BREAKPOINT macro. This macro is enabled
  * unconditionally in all builds, including debug and optimized 
  * builds.
  */
@@ -40,7 +40,7 @@
   do                                                    \
     {                                                   \
       std::cout << msg << std::endl;			\
-      ns3::AssertBreakpoint ();                         \
+      NS_BREAKPOINT ();                                 \
     }                                                   \
   while (false)
 
--- a/src/core/uid-manager.cc	Thu Aug 02 08:55:56 2007 +0200
+++ b/src/core/uid-manager.cc	Thu Aug 02 13:59:08 2007 +0100
@@ -20,6 +20,7 @@
  */
 #include "uid-manager.h"
 #include "ns3/fatal-error.h"
+#include "ns3/assert.h"
 
 
 namespace ns3 {
--- a/src/core/wscript	Thu Aug 02 08:55:56 2007 +0200
+++ b/src/core/wscript	Thu Aug 02 13:59:08 2007 +0100
@@ -15,6 +15,12 @@
     e.define = 'HAVE_GETENV'
     e.run()
 
+    e = conf.create_header_configurator()
+    e.mandatory = False
+    e.name = 'signal.h'
+    e.define = 'HAVE_SIGNAL_H'
+    e.run()
+
     conf.write_config_header('ns3/core-config.h')
 
 
@@ -26,7 +32,7 @@
     core.source = [
         'callback-test.cc',
         'debug.cc',
-        'assert.cc',
+        'breakpoint.cc',
         'ptr.cc',
         'object.cc',
         'test.cc',
@@ -58,6 +64,7 @@
         'object.h',
         'debug.h',
         'assert.h',
+        'breakpoint.h',
         'fatal-error.h',
         'test.h',
         'random-variable.h',