From c577b059b472b6b742548824f0f885b859ad62eb Mon Sep 17 00:00:00 2001
From: Ben Pfaff <blp@cs.stanford.edu>
Date: Fri, 8 Dec 2006 18:47:37 +0000
Subject: [PATCH] Make it possible to ignore page faults in GDB. From
 su.class.cs140 and Godmar Back.

---
 doc/debug.texi                             |  4 ++
 doc/installation.texi                      | 12 ++++
 src/misc/bochs-2.2.6-build.sh              |  2 +
 src/misc/bochs-2.2.6-page-fault-segv.patch | 76 ++++++++++++++++++++++
 src/misc/bochs-2.2.6-paranoia.patch        | 19 ++++++
 5 files changed, 113 insertions(+)
 create mode 100644 src/misc/bochs-2.2.6-page-fault-segv.patch
 create mode 100644 src/misc/bochs-2.2.6-paranoia.patch

diff --git a/doc/debug.texi b/doc/debug.texi
index 1aea238..0d5a79d 100644
--- a/doc/debug.texi
+++ b/doc/debug.texi
@@ -444,6 +444,10 @@ in your kernel, because your kernel should never crash.  Starting with
 Project 3, the situation will change if you use @func{get_user} and
 @func{put_user} strategy to verify user memory accesses
 (@pxref{Accessing User Memory}).
+
+If you don't want GDB to stop for page faults, then issue the command
+@code{handle SIGSEGV nostop}.  GDB will still print a message for
+every page fault, but it will not come back to a command prompt.
 @end deffn
 
 @node Example GDB Session
diff --git a/doc/installation.texi b/doc/installation.texi
index c15c125..0fc7b06 100644
--- a/doc/installation.texi
+++ b/doc/installation.texi
@@ -172,6 +172,16 @@ harmless elsewhere.
 Needed for Bochs to compile in terminal support on Solaris
 hosts.  Probably harmless elsewhere.
 
+@item bochs-2.2.6-page-fault-segv.patch
+
+Makes the GDB stub report a SIGSEGV to the debugger when a page-fault
+exception occurs, instead of ``signal 0.''  The former can be ignored
+with @code{handle SIGSEGV nostop} but the latter cannot.
+
+@item bochs-2.2.6-paranoia.patch
+
+Fixes compile error with modern versions of GCC.
+
 @item bochs-2.2.6-solaris-link.patch
 
 Needed on Solaris hosts.  Do not apply it elsewhere.
@@ -185,6 +195,8 @@ patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-jitter.patch
 patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-triple-fault.patch
 patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-ms-extensions.patch
 patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-solaris-tty.patch
+patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-page-fault-segv.patch
+patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-paranoia.patch
 patch -p1 < $PINTOSDIR/src/misc/bochs-2.2.6-solaris-link.patch
 @end example
 @noindent
diff --git a/src/misc/bochs-2.2.6-build.sh b/src/misc/bochs-2.2.6-build.sh
index ad97596..6c07a98 100755
--- a/src/misc/bochs-2.2.6-build.sh
+++ b/src/misc/bochs-2.2.6-build.sh
@@ -19,6 +19,8 @@ cat $PINTOSDIR/src/misc/bochs-2.2.6-big-endian.patch | patch -p1
 cat $PINTOSDIR/src/misc/bochs-2.2.6-jitter.patch | patch -p1
 cat $PINTOSDIR/src/misc/bochs-2.2.6-triple-fault.patch | patch -p1
 cat $PINTOSDIR/src/misc/bochs-2.2.6-solaris-tty.patch | patch -p1
+cat $PINTOSDIR/src/misc/bochs-2.2.6-page-fault-segv.patch | patch -p1
+cat $PINTOSDIR/src/misc/bochs-2.2.6-paranoia.patch | patch -p1
 if test "`uname -s`" = "SunOS"; then
     cat $PINTOSDIR/src/misc/bochs-2.2.6-solaris-link.patch | patch -p1
 fi
diff --git a/src/misc/bochs-2.2.6-page-fault-segv.patch b/src/misc/bochs-2.2.6-page-fault-segv.patch
new file mode 100644
index 0000000..81e59a7
--- /dev/null
+++ b/src/misc/bochs-2.2.6-page-fault-segv.patch
@@ -0,0 +1,76 @@
+Index: bochs-2.2.6/cpu/exception.cc
+diff -u bochs-2.2.6/cpu/exception.cc\~ bochs-2.2.6/cpu/exception.cc
+--- bochs-2.2.6/cpu/exception.cc~ 2006-09-28 15:51:39.000000000 -0700
++++ bochs-2.2.6/cpu/exception.cc 2006-12-08 11:14:33.000000000 -0800
+@@ -1033,6 +1033,7 @@ void BX_CPU_C::exception(unsigned vector
+     BX_CPU_THIS_PTR curr_exception[0] = exception_type;
+   }
+ 
++  bx_gdbstub_exception(vector);
+ #if BX_CPU_LEVEL >= 2
+   if (!real_mode()) {
+     BX_CPU_THIS_PTR interrupt(vector, 0, push_error, error_code);
+Index: bochs-2.2.6/gdbstub.cc
+diff -u bochs-2.2.6/gdbstub.cc\~ bochs-2.2.6/gdbstub.cc
+--- bochs-2.2.6/gdbstub.cc~ 2006-09-28 15:51:39.000000000 -0700
++++ bochs-2.2.6/gdbstub.cc 2006-12-08 11:12:03.000000000 -0800
+@@ -26,6 +26,7 @@ static int last_stop_reason = GDBSTUB_ST
+ #define GDBSTUB_EXECUTION_BREAKPOINT    (0xac1)
+ #define GDBSTUB_TRACE                   (0xac2)
+ #define GDBSTUB_USER_BREAK              (0xac3)
++#define GDBSTUB_EXCEPTION_0E            (0xac4)
+ 
+ static int listen_socket_fd;
+ static int socket_fd;
+@@ -271,6 +272,12 @@ int bx_gdbstub_check(unsigned int eip)
+    return(GDBSTUB_STOP_NO_REASON);
+ }
+ 
++void bx_gdbstub_exception(unsigned int nr) 
++{
++    if (nr == 0x0e)
++        last_stop_reason = GDBSTUB_EXCEPTION_0E;
++}
++
+ static int remove_breakpoint(unsigned int addr, int len)
+ {
+    unsigned int i;
+@@ -452,6 +459,10 @@ static void debug_loop(void)
+                    {
+                       write_signal(&buf[1], SIGTRAP);
+                    }
++                 else if (last_stop_reason == GDBSTUB_EXCEPTION_0E)
++                   {
++                      write_signal(&buf[1], SIGSEGV);
++                   }
+                  else
+                    {
+                       write_signal(&buf[1], 0);
+@@ -476,10 +487,14 @@ static void debug_loop(void)
+                    {
+                       write_signal(&buf[1], SIGTRAP);
+                    }
+-                 else
++                 else if (last_stop_reason == GDBSTUB_EXCEPTION_0E)
+                    {
+                       write_signal(&buf[1], SIGSEGV);
+                    }
++                 else
++                   {
++                      write_signal(&buf[1], 0);
++                   }
+                  put_reply(buf);
+                  break;
+               }
+Index: bochs-2.2.6/bochs.h
+diff -u bochs-2.2.6/bochs.h\~ bochs-2.2.6/bochs.h
+--- bochs-2.2.6/bochs.h~ 2006-09-28 15:51:39.000000000 -0700
++++ bochs-2.2.6/bochs.h 2006-12-08 11:14:19.000000000 -0800
+@@ -375,6 +375,7 @@ BOCHSAPI extern logfunc_t *genlog;
+ // defines for GDB stub
+ void bx_gdbstub_init(int argc, char* argv[]);
+ int bx_gdbstub_check(unsigned int eip);
++void bx_gdbstub_exception(unsigned int nr);
+ #define GDBSTUB_STOP_NO_REASON   (0xac0)
+ 
+ #if BX_SUPPORT_SMP
diff --git a/src/misc/bochs-2.2.6-paranoia.patch b/src/misc/bochs-2.2.6-paranoia.patch
new file mode 100644
index 0000000..ff8d736
--- /dev/null
+++ b/src/misc/bochs-2.2.6-paranoia.patch
@@ -0,0 +1,19 @@
+Index: bochs-2.2.6/iodev/hdimage.h
+diff -u bochs-2.2.6/iodev/hdimage.h\~ bochs-2.2.6/iodev/hdimage.h
+--- bochs-2.2.6/iodev/hdimage.h~ 2005-11-06 03:07:01.000000000 -0800
++++ bochs-2.2.6/iodev/hdimage.h 2006-09-28 15:55:50.000000000 -0700
+@@ -273,14 +273,8 @@ class sparse_image_t : public device_ima
+ 
+  void panic(const char * message);
+  off_t
+-#ifndef PARANOID
+-       sparse_image_t::
+-#endif
+                        get_physical_offset();
+  void
+-#ifndef PARANOID
+-       sparse_image_t::
+-#endif
+                        set_virtual_page(Bit32u new_virtual_page);
+  void read_header();
+  ssize_t read_page_fragment(Bit32u read_virtual_page, Bit32u read_page_offset, size_t read_size, void * buf);
-- 
2.30.2