Browse Source

gdb-microbaze: split off big patch, so update-patches works

Waldemar Brodkorb 9 years ago
parent
commit
047d8328a9
26 changed files with 1927 additions and 1862 deletions
  1. 0 1848
      package/gdb-microblaze/patches/microblaze.patch
  2. 14 0
      package/gdb-microblaze/patches/patch-bfd_bfd-in2_h
  3. 202 0
      package/gdb-microblaze/patches/patch-bfd_elf32-microblaze_c
  4. 10 0
      package/gdb-microblaze/patches/patch-bfd_libbfd_h
  5. 20 0
      package/gdb-microblaze/patches/patch-gdb_Makefile_in
  6. 3 3
      package/gdb-microblaze/patches/patch-gdb_common_linux-ptrace_h
  7. 3 3
      package/gdb-microblaze/patches/patch-gdb_common_signals_c
  8. 13 0
      package/gdb-microblaze/patches/patch-gdb_config_microblaze_linux_mh
  9. 19 0
      package/gdb-microblaze/patches/patch-gdb_configure_host
  10. 14 0
      package/gdb-microblaze/patches/patch-gdb_configure_tgt
  11. 51 0
      package/gdb-microblaze/patches/patch-gdb_debugreg_h
  12. 27 0
      package/gdb-microblaze/patches/patch-gdb_gdbserver_Makefile_in
  13. 4 4
      package/gdb-microblaze/patches/patch-gdb_gdbserver_configure
  14. 16 0
      package/gdb-microblaze/patches/patch-gdb_gdbserver_configure_srv
  15. 232 0
      package/gdb-microblaze/patches/patch-gdb_gdbserver_linux-microblaze-low_c
  16. 4 4
      package/gdb-microblaze/patches/patch-gdb_linux-nat_c
  17. 433 0
      package/gdb-microblaze/patches/patch-gdb_microblaze-linux-nat_c
  18. 155 0
      package/gdb-microblaze/patches/patch-gdb_microblaze-linux-tdep_c
  19. 18 0
      package/gdb-microblaze/patches/patch-gdb_microblaze-rom_c
  20. 467 0
      package/gdb-microblaze/patches/patch-gdb_microblaze-tdep_c
  21. 91 0
      package/gdb-microblaze/patches/patch-gdb_microblaze-tdep_h
  22. 44 0
      package/gdb-microblaze/patches/patch-gdb_regformats_reg-microblaze_dat
  23. 33 0
      package/gdb-microblaze/patches/patch-gdb_sgidefs_h
  24. 10 0
      package/gdb-microblaze/patches/patch-include_elf_microblaze_h
  25. 29 0
      package/gdb-microblaze/patches/patch-opcodes_microblaze-opc_h
  26. 15 0
      package/gdb-microblaze/patches/patch-opcodes_microblaze-opcm_h

+ 0 - 1848
package/gdb-microblaze/patches/microblaze.patch

@@ -1,1848 +0,0 @@
-diff -Nur gdb-7.8.2.orig/bfd/bfd-in2.h gdb-7.8.2/bfd/bfd-in2.h
---- gdb-7.8.2.orig/bfd/bfd-in2.h	2015-01-15 11:58:11.000000000 +0100
-+++ gdb-7.8.2/bfd/bfd-in2.h	2016-05-14 21:29:38.989383220 +0200
-@@ -5449,6 +5449,11 @@
- expressions of the form "Symbol Op Symbol"  */
-   BFD_RELOC_MICROBLAZE_32_SYM_OP_SYM,
- 
-+/* This is a 32 bit reloc that stores the 32 bit pc relative
-+value in two words (with an imm instruction).  No relocation is 
-+done here - only used for relaxing  */
-+  BFD_RELOC_MICROBLAZE_32_NONE,
-+
- /* This is a 64 bit reloc that stores the 32 bit pc relative
- value in two words (with an imm instruction).  No relocation is
- done here - only used for relaxing  */
-diff -Nur gdb-7.8.2.orig/bfd/elf32-microblaze.c gdb-7.8.2/bfd/elf32-microblaze.c
---- gdb-7.8.2.orig/bfd/elf32-microblaze.c	2015-01-15 11:58:11.000000000 +0100
-+++ gdb-7.8.2/bfd/elf32-microblaze.c	2016-05-14 21:29:38.993383375 +0200
-@@ -177,6 +177,20 @@
-           FALSE), 		/* PC relative offset?  */
- 
-    /* This reloc does nothing.  Used for relaxation.  */
-+   HOWTO (R_MICROBLAZE_32_NONE,	/* Type.  */
-+          0,			/* Rightshift.  */
-+          2,			/* Size (0 = byte, 1 = short, 2 = long).  */
-+          32,			/* Bitsize.  */
-+          TRUE,			/* PC_relative.  */
-+          0,			/* Bitpos.  */
-+          complain_overflow_bitfield,  /* Complain on overflow.  */
-+          NULL,                  /* Special Function.  */
-+          "R_MICROBLAZE_32_NONE",/* Name.  */
-+          FALSE,		/* Partial Inplace.  */
-+          0,			/* Source Mask.  */
-+          0,			/* Dest Mask.  */
-+          FALSE),		/* PC relative offset?  */
-+
-    HOWTO (R_MICROBLAZE_64_NONE,	/* Type.  */
-           0,			/* Rightshift.  */
-           2,			/* Size (0 = byte, 1 = short, 2 = long).  */
-@@ -532,7 +546,10 @@
-     case BFD_RELOC_NONE:
-       microblaze_reloc = R_MICROBLAZE_NONE;
-       break;
--    case BFD_RELOC_MICROBLAZE_64_NONE:
-+    case BFD_RELOC_MICROBLAZE_32_NONE:
-+      microblaze_reloc = R_MICROBLAZE_32_NONE;
-+      break;
-+     case BFD_RELOC_MICROBLAZE_64_NONE:
-       microblaze_reloc = R_MICROBLAZE_64_NONE;
-       break;
-     case BFD_RELOC_32:
-@@ -668,6 +685,67 @@
-   return _bfd_elf_is_local_label_name (abfd, name);
- }
- 
-+/* Support for core dump NOTE sections.  */
-+static bfd_boolean
-+microblaze_elf_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
-+{
-+  int offset;
-+  unsigned int size;
-+
-+  switch (note->descsz)
-+    {
-+      default:
-+        return FALSE;
-+
-+      case 228:         /* Linux/MicroBlaze */
-+        /* pr_cursig */
-+        elf_tdata (abfd)->core->signal = bfd_get_16 (abfd, note->descdata + 12);
-+
-+        /* pr_pid */
-+        elf_tdata (abfd)->core->pid = bfd_get_32 (abfd, note->descdata + 24);
-+
-+        /* pr_reg */
-+        offset = 72;
-+        size = 50 * 4;
-+
-+        break;
-+    }
-+
-+  /* Make a ".reg/999" section.  */
-+  return _bfd_elfcore_make_pseudosection (abfd, ".reg",
-+                                          size, note->descpos + offset);
-+}
-+
-+static bfd_boolean
-+microblaze_elf_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
-+{
-+  switch (note->descsz)
-+    {
-+      default:
-+        return FALSE;
-+
-+      case 128:         /* Linux/MicroBlaze elf_prpsinfo */
-+        elf_tdata (abfd)->core->program
-+         = _bfd_elfcore_strndup (abfd, note->descdata + 32, 16);
-+        elf_tdata (abfd)->core->command
-+         = _bfd_elfcore_strndup (abfd, note->descdata + 48, 80);
-+    }
-+
-+  /* Note that for some reason, a spurious space is tacked
-+     onto the end of the args in some (at least one anyway)
-+     implementations, so strip it off if it exists.  */
-+
-+  {
-+    char *command = elf_tdata (abfd)->core->command;
-+    int n = strlen (command);
-+
-+    if (0 < n && command[n - 1] == ' ')
-+      command[n - 1] = '\0';
-+  }
-+
-+  return TRUE;
-+}
-+
- /* The microblaze linker (like many others) needs to keep track of
-    the number of relocs that it decides to copy as dynamic relocs in
-    check_relocs for each symbol. This is so that it can later discard
-@@ -1023,7 +1101,7 @@
- 	    {
- 	      /* External symbol.  */
- 	      bfd_boolean warned ATTRIBUTE_UNUSED;
--	      bfd_boolean ignored ATTRIBUTE_UNUSED;
-+	      bfd_boolean ignored;
- 
- 	      RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
- 				       r_symndx, symtab_hdr, sym_hashes,
-@@ -1852,14 +1930,22 @@
- 	        }
- 	      break;
- 	    case R_MICROBLAZE_NONE:
-+	    case R_MICROBLAZE_32_NONE:
- 	      {
- 	        /* This was a PC-relative instruction that was
-  		   completely resolved.  */
- 	        int sfix, efix;
-+		unsigned int val;
- 	        bfd_vma target_address;
- 	        target_address = irel->r_addend + irel->r_offset;
- 	        sfix = calc_fixup (irel->r_offset, 0, sec);
- 	        efix = calc_fixup (target_address, 0, sec);
-+
-+                /* Validate the in-band val.  */
-+                val = bfd_get_32 (abfd, contents + irel->r_offset);
-+                if (val != irel->r_addend && ELF32_R_TYPE (irel->r_info) == R_MICROBLAZE_32_NONE) {
-+                    fprintf(stderr, "%d: CORRUPT relax reloc %x %lx\n", __LINE__, val, irel->r_addend);
-+                }
- 	        irel->r_addend -= (efix - sfix);
- 	        /* Should use HOWTO.  */
- 	        microblaze_bfd_write_imm_value_32 (abfd, contents + irel->r_offset,
-@@ -1907,6 +1993,49 @@
-           irelscanend = irelocs + o->reloc_count;
-           for (irelscan = irelocs; irelscan < irelscanend; irelscan++)
-             {
-+              if (1 && ELF32_R_TYPE (irelscan->r_info) == (int) R_MICROBLAZE_32_NONE)
-+                {
-+                  unsigned int val;
-+
-+                  isym = isymbuf + ELF32_R_SYM (irelscan->r_info);
-+
-+                  /* hax: We only do the following fixup for debug location lists.  */
-+                  if (strcmp(".debug_loc", o->name))
-+                    continue;
-+
-+                  /* This was a PC-relative instruction that was completely resolved.  */
-+                  if (ocontents == NULL)
-+                    {
-+		      if (elf_section_data (o)->this_hdr.contents != NULL)
-+		          ocontents = elf_section_data (o)->this_hdr.contents;
-+		      else
-+		        {
-+		          /* We always cache the section contents.
-+			     Perhaps, if info->keep_memory is FALSE, we
-+			     should free them, if we are permitted to.  */
-+
-+		          if (o->rawsize == 0)
-+			      o->rawsize = o->size;
-+		          ocontents = (bfd_byte *) bfd_malloc (o->rawsize);
-+		          if (ocontents == NULL)
-+			      goto error_return;
-+		          if (!bfd_get_section_contents (abfd, o, ocontents,
-+                                                         (file_ptr) 0,
-+                                                         o->rawsize))
-+                              goto error_return;
-+		          elf_section_data (o)->this_hdr.contents = ocontents;
-+		        }
-+		    }
-+
-+                  val = bfd_get_32 (abfd, ocontents + irelscan->r_offset);
-+                  if (val != irelscan->r_addend) {
-+			fprintf(stderr, "%d: CORRUPT relax reloc! %x %lx\n", __LINE__, val, irelscan->r_addend);
-+                  }
-+
-+                  irelscan->r_addend -= calc_fixup (irelscan->r_addend, 0, sec);
-+                  microblaze_bfd_write_imm_value_32 (abfd, ocontents + irelscan->r_offset,
-+                                                     irelscan->r_addend);
-+              }
-               if (ELF32_R_TYPE (irelscan->r_info) == (int) R_MICROBLAZE_32)
-                 {
- 	          isym = isymbuf + ELF32_R_SYM (irelscan->r_info);
-@@ -1966,7 +2095,7 @@
- 			      elf_section_data (o)->this_hdr.contents = ocontents;
- 			    }
- 			}
--		      irelscan->r_addend -= calc_fixup (irel->r_addend
-+		      irelscan->r_addend -= calc_fixup (irelscan->r_addend
- 							+ isym->st_value,
- 							0,
- 							sec);
-@@ -3506,4 +3635,7 @@
- #define elf_backend_size_dynamic_sections       microblaze_elf_size_dynamic_sections
- #define elf_backend_add_symbol_hook		microblaze_elf_add_symbol_hook
- 
-+#define elf_backend_grok_prstatus               microblaze_elf_grok_prstatus
-+#define elf_backend_grok_psinfo                 microblaze_elf_grok_psinfo
-+
- #include "elf32-target.h"
-diff -Nur gdb-7.8.2.orig/bfd/libbfd.h gdb-7.8.2/bfd/libbfd.h
---- gdb-7.8.2.orig/bfd/libbfd.h	2015-01-15 11:58:11.000000000 +0100
-+++ gdb-7.8.2/bfd/libbfd.h	2016-05-14 21:29:38.993383375 +0200
-@@ -2644,6 +2644,7 @@
-   "BFD_RELOC_MICROBLAZE_32_ROSDA",
-   "BFD_RELOC_MICROBLAZE_32_RWSDA",
-   "BFD_RELOC_MICROBLAZE_32_SYM_OP_SYM",
-+  "BFD_RELOC_MICROBLAZE_32_NONE",
-   "BFD_RELOC_MICROBLAZE_64_NONE",
-   "BFD_RELOC_MICROBLAZE_64_GOTPC",
-   "BFD_RELOC_MICROBLAZE_64_GOT",
-diff -Nur gdb-7.8.2.orig/gdb/config/microblaze/linux.mh gdb-7.8.2/gdb/config/microblaze/linux.mh
---- gdb-7.8.2.orig/gdb/config/microblaze/linux.mh	1970-01-01 01:00:00.000000000 +0100
-+++ gdb-7.8.2/gdb/config/microblaze/linux.mh	2016-05-14 21:29:38.993383375 +0200
-@@ -0,0 +1,10 @@
-+# Host: Microblaze, running Linux
-+
-+NAT_FILE= config/nm-linux.h
-+NATDEPFILES= inf-ptrace.o fork-child.o \
-+	microblaze-linux-nat.o proc-service.o linux-thread-db.o \
-+	linux-nat.o linux-osdata.o linux-fork.o linux-procfs.o linux-ptrace.o \
-+	linux-waitpid.o
-+NAT_CDEPS = $(srcdir)/proc-service.list
-+
-+LOADLIBES = -ldl $(RDYNAMIC)
-diff -Nur gdb-7.8.2.orig/gdb/configure.host gdb-7.8.2/gdb/configure.host
---- gdb-7.8.2.orig/gdb/configure.host	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/configure.host	2016-05-14 21:29:38.993383375 +0200
-@@ -59,6 +59,7 @@
- m68*)			gdb_host_cpu=m68k ;;
- m88*)			gdb_host_cpu=m88k ;;
- mips*)			gdb_host_cpu=mips ;;
-+microblaze*)		gdb_host_cpu=microblaze ;;
- powerpc* | rs6000)	gdb_host_cpu=powerpc ;;
- sparcv9 | sparc64)	gdb_host_cpu=sparc ;;
- s390*)			gdb_host_cpu=s390 ;;
-@@ -133,6 +134,8 @@
- 			gdb_host=nbsd ;;
- mips64*-*-openbsd*)	gdb_host=obsd64 ;;
- 
-+microblaze*-*linux*)    gdb_host=linux ;;
-+
- powerpc-*-aix* | rs6000-*-* | powerpc64-*-aix*)
- 			gdb_host=aix ;;
- powerpc*-*-freebsd*)	gdb_host=fbsd ;;
-diff -Nur gdb-7.8.2.orig/gdb/configure.tgt gdb-7.8.2/gdb/configure.tgt
---- gdb-7.8.2.orig/gdb/configure.tgt	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/configure.tgt	2016-05-14 21:29:38.993383375 +0200
-@@ -340,9 +340,10 @@
- 
- microblaze*-linux-*|microblaze*-*-linux*)
- 	# Target: Xilinx MicroBlaze running Linux
--	gdb_target_obs="microblaze-tdep.o microblaze-linux-tdep.o microblaze-rom.o \
-+	gdb_target_obs="microblaze-tdep.o microblaze-linux-tdep.o microblaze-rom.o glibc-tdep.o \
- 			monitor.o dsrec.o solib-svr4.o symfile-mem.o linux-tdep.o"
- 	gdb_sim=../sim/microblaze/libsim.a
-+	build_gdbserver=yes
- 	;;
- microblaze*-*-*)
- 	# Target: Xilinx MicroBlaze running standalone
-diff -Nur gdb-7.8.2.orig/gdb/gdbserver/configure.srv gdb-7.8.2/gdb/gdbserver/configure.srv
---- gdb-7.8.2.orig/gdb/gdbserver/configure.srv	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/gdbserver/configure.srv	2016-05-14 21:29:38.993383375 +0200
-@@ -198,6 +198,13 @@
- 			srv_linux_usrregs=yes
- 			srv_linux_thread_db=yes
- 			;;
-+  microblaze*-*-linux*)	srv_regobj=microblaze-linux.o
-+			srv_tgtobj="$srv_linux_obj linux-microblaze-low.o"
-+			srv_linux_usrregs=yes
-+			srv_linux_regsets=yes
-+			srv_linux_thread_db=yes
-+			;;
-+
-   nios2*-*-linux*)	srv_regobj="nios2-linux.o"
- 			srv_tgtobj="$srv_linux_obj linux-nios2-low.o"
- 			srv_xmlfiles="nios2-linux.xml"
-diff -Nur gdb-7.8.2.orig/gdb/gdbserver/linux-microblaze-low.c gdb-7.8.2/gdb/gdbserver/linux-microblaze-low.c
---- gdb-7.8.2.orig/gdb/gdbserver/linux-microblaze-low.c	1970-01-01 01:00:00.000000000 +0100
-+++ gdb-7.8.2/gdb/gdbserver/linux-microblaze-low.c	2016-05-14 21:29:38.993383375 +0200
-@@ -0,0 +1,228 @@
-+/* GNU/Linux/Microblaze specific low level interface, for the remote server for
-+   GDB.
-+   Copyright (C) 1995-2013 Free Software Foundation, Inc.
-+
-+   This file is part of GDB.
-+
-+   This program is free software; you can redistribute it and/or modify
-+   it under the terms of the GNU General Public License as published by
-+   the Free Software Foundation; either version 3 of the License, or
-+   (at your option) any later version.
-+
-+   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, see <http://www.gnu.org/licenses/>.  */
-+
-+#include "server.h"
-+#include "linux-low.h"
-+
-+#include <asm/ptrace.h>
-+#include <sys/procfs.h>
-+#include <sys/ptrace.h>
-+
-+#include "gdb_proc_service.h"
-+
-+static int microblaze_regmap[] =
-+ {PT_GPR(0),     PT_GPR(1),     PT_GPR(2),     PT_GPR(3),
-+  PT_GPR(4),     PT_GPR(5),     PT_GPR(6),     PT_GPR(7),
-+  PT_GPR(8),     PT_GPR(9),     PT_GPR(10),    PT_GPR(11),
-+  PT_GPR(12),    PT_GPR(13),    PT_GPR(14),    PT_GPR(15),
-+  PT_GPR(16),    PT_GPR(17),    PT_GPR(18),    PT_GPR(19),
-+  PT_GPR(20),    PT_GPR(21),    PT_GPR(22),    PT_GPR(23),
-+  PT_GPR(24),    PT_GPR(25),    PT_GPR(26),    PT_GPR(27),
-+  PT_GPR(28),    PT_GPR(29),    PT_GPR(30),    PT_GPR(31),
-+  PT_PC,         PT_MSR,        PT_EAR,        PT_ESR,
-+  PT_FSR
-+  };
-+
-+#define microblaze_num_regs (sizeof microblaze_regmap / sizeof microblaze_regmap[0])
-+
-+/* Defined in auto-generated file microblaze-linux.c.  */
-+void init_registers_microblaze (void);
-+extern const struct target_desc *tdesc_microblaze;
-+
-+static int
-+microblaze_cannot_store_register (int regno)
-+{
-+  if (microblaze_regmap[regno] == -1 || regno == 0)
-+    return 1;
-+
-+  return 0;
-+}
-+
-+static int
-+microblaze_cannot_fetch_register (int regno)
-+{
-+  return 0;
-+}
-+
-+static CORE_ADDR
-+microblaze_get_pc (struct regcache *regcache)
-+{
-+  unsigned long pc;
-+
-+  collect_register_by_name (regcache, "pc", &pc);
-+  return (CORE_ADDR) pc;
-+}
-+
-+static void
-+microblaze_set_pc (struct regcache *regcache, CORE_ADDR pc)
-+{
-+  unsigned long newpc = pc;
-+
-+  supply_register_by_name (regcache, "pc", &newpc);
-+}
-+
-+/* dbtrap insn */
-+/* brki r16, 0x18; */
-+static const unsigned long microblaze_breakpoint = 0xba0c0018;
-+#define microblaze_breakpoint_len 4
-+
-+static int
-+microblaze_breakpoint_at (CORE_ADDR where)
-+{
-+  unsigned long insn;
-+
-+  (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
-+  if (insn == microblaze_breakpoint)
-+    return 1;
-+  /* If necessary, recognize more trap instructions here.  GDB only uses the
-+     one.  */
-+  return 0;
-+}
-+
-+static CORE_ADDR
-+microblaze_reinsert_addr (struct regcache *regcache)
-+{
-+  unsigned long pc;
-+  collect_register_by_name (regcache, "r15", &pc);
-+  return pc;
-+}
-+
-+#ifdef HAVE_PTRACE_GETREGS
-+
-+static void
-+microblaze_collect_ptrace_register (struct regcache *regcache, int regno, char *buf)
-+{
-+  int size = register_size (regcache->tdesc, regno);
-+
-+  memset (buf, 0, sizeof (long));
-+
-+  if (size < sizeof (long))
-+    collect_register (regcache, regno, buf + sizeof (long) - size);
-+  else
-+    collect_register (regcache, regno, buf);
-+}
-+
-+static void
-+microblaze_supply_ptrace_register (struct regcache *regcache,
-+			    int regno, const char *buf)
-+{
-+  int size = register_size (regcache->tdesc, regno);
-+
-+  if (regno == 0) {
-+    unsigned long regbuf_0 = 0;
-+    /* clobbering r0 so that it is always 0 as enforced by hardware */
-+    supply_register (regcache, regno, (const char*)&regbuf_0);
-+  } else {
-+      if (size < sizeof (long))
-+        supply_register (regcache, regno, buf + sizeof (long) - size);
-+      else
-+        supply_register (regcache, regno, buf);
-+  }
-+}
-+
-+/* Provide only a fill function for the general register set.  ps_lgetregs
-+   will use this for NPTL support.  */
-+
-+static void microblaze_fill_gregset (struct regcache *regcache, void *buf)
-+{
-+  int i;
-+
-+  for (i = 0; i < 32; i++)
-+    microblaze_collect_ptrace_register (regcache, i, (char *) buf + microblaze_regmap[i]);
-+}
-+
-+static void
-+microblaze_store_gregset (struct regcache *regcache, const void *buf)
-+{
-+  int i;
-+
-+  for (i = 0; i < 32; i++)
-+    supply_register (regcache, i, (char *) buf + microblaze_regmap[i]);
-+}
-+
-+#endif /* HAVE_PTRACE_GETREGS */
-+
-+static struct regset_info microblaze_regsets[] = {
-+#ifdef HAVE_PTRACE_GETREGS
-+  { PTRACE_GETREGS, PTRACE_SETREGS, 0, sizeof (elf_gregset_t), GENERAL_REGS, microblaze_fill_gregset, microblaze_store_gregset },
-+  { 0, 0, 0, -1, -1, NULL, NULL },
-+#endif /* HAVE_PTRACE_GETREGS */
-+  { 0, 0, 0, -1, -1, NULL, NULL }
-+};
-+
-+static struct regsets_info microblaze_regsets_info =
-+  {
-+    microblaze_regsets, /* regsets */
-+    0, /* num_regsets */
-+    NULL, /* disabled_regsets */
-+  };
-+
-+static struct usrregs_info microblaze_usrregs_info =
-+  {
-+    microblaze_num_regs,
-+    microblaze_regmap,
-+  };
-+
-+static struct regs_info regs_info =
-+  {
-+    NULL, /* regset_bitmap */
-+    &microblaze_usrregs_info,
-+    &microblaze_regsets_info
-+  };
-+
-+static const struct regs_info *
-+microblaze_regs_info (void)
-+{
-+  return &regs_info;
-+}
-+
-+static void
-+microblaze_arch_setup (void)
-+{
-+  current_process ()->tdesc = tdesc_microblaze;
-+}
-+
-+struct linux_target_ops the_low_target = {
-+  microblaze_arch_setup,
-+  microblaze_regs_info,
-+  microblaze_cannot_fetch_register,
-+  microblaze_cannot_store_register,
-+  NULL, /* fetch_register */
-+  microblaze_get_pc,
-+  microblaze_set_pc,
-+  (const unsigned char *) &microblaze_breakpoint,
-+  microblaze_breakpoint_len,
-+  microblaze_reinsert_addr,
-+  0,
-+  microblaze_breakpoint_at,
-+  NULL,
-+  NULL,
-+  NULL,
-+  NULL,
-+  microblaze_collect_ptrace_register,
-+  microblaze_supply_ptrace_register,
-+};
-+
-+void
-+initialize_low_arch (void)
-+{
-+  init_registers_microblaze ();
-+
-+  initialize_regsets_info (&microblaze_regsets_info);
-+}
-\ No newline at end of file
-diff -Nur gdb-7.8.2.orig/gdb/gdbserver/Makefile.in gdb-7.8.2/gdb/gdbserver/Makefile.in
---- gdb-7.8.2.orig/gdb/gdbserver/Makefile.in	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/gdbserver/Makefile.in	2016-05-14 21:29:38.993383375 +0200
-@@ -148,6 +148,7 @@
- 	$(srcdir)/linux-ia64-low.c $(srcdir)/linux-low.c \
- 	$(srcdir)/linux-m32r-low.c \
- 	$(srcdir)/linux-m68k-low.c $(srcdir)/linux-mips-low.c \
-+	$(srcdir)/linux-microblaze-low.c \
- 	$(srcdir)/linux-nios2-low.c \
- 	$(srcdir)/linux-ppc-low.c \
- 	$(srcdir)/linux-s390-low.c \
-@@ -329,6 +330,7 @@
- 	rm -f arm-with-iwmmxt.c
- 	rm -f arm-with-vfpv2.c arm-with-vfpv3.c arm-with-neon.c
- 	rm -f mips-linux.c mips64-linux.c
-+	rm -f microblaze-linux.c
- 	rm -f nios2-linux.c
- 	rm -f powerpc-32.c powerpc-32l.c powerpc-64l.c powerpc-e500l.c
- 	rm -f powerpc-altivec32l.c powerpc-cell32l.c powerpc-vsx32l.c
-@@ -620,6 +622,8 @@
- 	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/mips64-linux.dat mips64-linux.c
- mips64-dsp-linux.c : $(srcdir)/../regformats/mips64-dsp-linux.dat $(regdat_sh)
- 	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/mips64-dsp-linux.dat mips64-dsp-linux.c
-+microblaze-linux.c : $(srcdir)/../regformats/reg-microblaze.dat $(regdat_sh)
-+	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/reg-microblaze.dat microblaze-linux.c
- nios2-linux.c :	$(srcdir)/../regformats/nios2-linux.dat $(regdat_sh)
- 	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/nios2-linux.dat nios2-linux.c
- powerpc-32.c : $(srcdir)/../regformats/rs6000/powerpc-32.dat $(regdat_sh)
-diff -Nur gdb-7.8.2.orig/gdb/Makefile.in gdb-7.8.2/gdb/Makefile.in
---- gdb-7.8.2.orig/gdb/Makefile.in	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/Makefile.in	2016-05-14 21:29:38.993383375 +0200
-@@ -912,7 +912,7 @@
- annotate.h sim-regno.h dictionary.h dfp.h main.h frame-unwind.h	\
- remote-fileio.h i386-linux-tdep.h vax-tdep.h objc-lang.h \
- sentinel-frame.h bcache.h symfile.h windows-tdep.h linux-tdep.h \
--gdb_usleep.h jit.h xml-syscall.h microblaze-tdep.h \
-+gdb_usleep.h jit.h xml-syscall.h microblaze-tdep.h microblaze-linux-tdep.h \
- psymtab.h psympriv.h progspace.h bfin-tdep.h ia64-hpux-tdep.h \
- amd64-darwin-tdep.h charset-list.h \
- config/djgpp/langinfo.h config/djgpp/nl_types.h darwin-nat.h \
-@@ -1639,7 +1639,7 @@
- 	m68kbsd-nat.c m68kbsd-tdep.c \
- 	m68klinux-nat.c m68klinux-tdep.c \
- 	m88k-tdep.c m88kbsd-nat.c \
--	microblaze-tdep.c microblaze-linux-tdep.c \
-+	microblaze-tdep.c microblaze-linux-nat.c microblaze-linux-tdep.c \
- 	mingw-hdep.c \
- 	mips-linux-nat.c mips-linux-tdep.c \
- 	mips-irix-tdep.c \
-diff -Nur gdb-7.8.2.orig/gdb/microblaze-linux-nat.c gdb-7.8.2/gdb/microblaze-linux-nat.c
---- gdb-7.8.2.orig/gdb/microblaze-linux-nat.c	1970-01-01 01:00:00.000000000 +0100
-+++ gdb-7.8.2/gdb/microblaze-linux-nat.c	2016-05-14 21:29:38.993383375 +0200
-@@ -0,0 +1,430 @@
-+/* Microblaze GNU/Linux native support.
-+
-+   Copyright (C) 1988-1989, 1991-1992, 1994, 1996, 2000-2012 Free
-+   Software Foundation, Inc.
-+
-+   This file is part of GDB.
-+
-+   This program is free software; you can redistribute it and/or modify
-+   it under the terms of the GNU General Public License as published by
-+   the Free Software Foundation; either version 3 of the License, or
-+   (at your option) any later version.
-+
-+   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, see <http://www.gnu.org/licenses/>.  */
-+
-+#include "defs.h"
-+#include "arch-utils.h"
-+#include "dis-asm.h"
-+#include "frame.h"
-+#include "trad-frame.h"
-+#include "symtab.h"
-+#include "value.h"
-+#include "gdbcmd.h"
-+#include "breakpoint.h"
-+#include "inferior.h"
-+#include "regcache.h"
-+#include "target.h"
-+#include "frame.h"
-+#include "frame-base.h"
-+#include "frame-unwind.h"
-+#include "dwarf2-frame.h"
-+#include "osabi.h"
-+
-+#include "gdb_assert.h"
-+#include "target-descriptions.h"
-+#include "opcodes/microblaze-opcm.h"
-+#include "opcodes/microblaze-dis.h"
-+
-+#include "linux-nat.h"
-+#include "target-descriptions.h"
-+
-+#include <sys/user.h>
-+#include <sys/utsname.h>
-+#include <sys/procfs.h>
-+#include <sys/ptrace.h>
-+
-+/* Prototypes for supply_gregset etc. */
-+#include "gregset.h"
-+
-+#include "microblaze-tdep.h"
-+
-+#include <elf/common.h>
-+#include "auxv.h"
-+
-+/* Defines ps_err_e, struct ps_prochandle.  */
-+#include "gdb_proc_service.h"
-+
-+/* On GNU/Linux, threads are implemented as pseudo-processes, in which
-+   case we may be tracing more than one process at a time.  In that
-+   case, inferior_ptid will contain the main process ID and the
-+   individual thread (process) ID.  get_thread_id () is used to get
-+   the thread id if it's available, and the process id otherwise.  */
-+
-+int
-+get_thread_id (ptid_t ptid)
-+{
-+  int tid = ptid_get_lwp (ptid);
-+  if (0 == tid)
-+    tid = ptid_get_pid (ptid);
-+  return tid;
-+}
-+
-+#define GET_THREAD_ID(PTID)	get_thread_id (PTID)
-+
-+/* Non-zero if our kernel may support the PTRACE_GETREGS and
-+   PTRACE_SETREGS requests, for reading and writing the
-+   general-purpose registers.  Zero if we've tried one of
-+   them and gotten an error.  */
-+int have_ptrace_getsetregs = 1;
-+
-+static int
-+microblaze_register_u_addr (struct gdbarch *gdbarch, int regno)
-+{
-+  int u_addr = -1;
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  /* NOTE: cagney/2003-11-25: This is the word size used by the ptrace
-+     interface, and not the wordsize of the program's ABI.  */
-+  int wordsize = sizeof (long);
-+
-+  /* General purpose registers occupy 1 slot each in the buffer.  */
-+  if (regno >= MICROBLAZE_R0_REGNUM
-+      && regno <= MICROBLAZE_FSR_REGNUM)
-+    u_addr = (regno * wordsize);
-+
-+  return u_addr;
-+}
-+
-+
-+static void
-+fetch_register (struct regcache *regcache, int tid, int regno)
-+{
-+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  /* This isn't really an address.  But ptrace thinks of it as one.  */
-+  CORE_ADDR regaddr = microblaze_register_u_addr (gdbarch, regno);
-+  int bytes_transferred;
-+  unsigned int offset;         /* Offset of registers within the u area.  */
-+  char buf[MAX_REGISTER_SIZE];
-+
-+  if (regaddr == -1)
-+  {
-+    memset (buf, '\0', register_size (gdbarch, regno));   /* Supply zeroes */
-+    regcache_raw_supply (regcache, regno, buf);
-+    return;
-+  }
-+
-+  /* Read the raw register using sizeof(long) sized chunks.  On a
-+     32-bit platform, 64-bit floating-point registers will require two
-+     transfers.  */
-+  for (bytes_transferred = 0;
-+       bytes_transferred < register_size (gdbarch, regno);
-+       bytes_transferred += sizeof (long))
-+  {
-+    long l;
-+
-+    errno = 0;
-+    l = ptrace (PTRACE_PEEKUSER, tid, (PTRACE_TYPE_ARG3) regaddr, 0);
-+    regaddr += sizeof (long);
-+    if (errno != 0)
-+    {
-+      char message[128];
-+      sprintf (message, "reading register %s (#%d)",
-+               gdbarch_register_name (gdbarch, regno), regno);
-+      perror_with_name (message);
-+    }
-+    memcpy (&buf[bytes_transferred], &l, sizeof (l));
-+  }
-+
-+  /* Now supply the register.  Keep in mind that the regcache's idea
-+     of the register's size may not be a multiple of sizeof
-+     (long).  */
-+  if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_LITTLE)
-+  {
-+    /* Little-endian values are always found at the left end of the
-+       bytes transferred.  */
-+    regcache_raw_supply (regcache, regno, buf);
-+  }
-+  else if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
-+  {
-+    /* Big-endian values are found at the right end of the bytes
-+       transferred.  */
-+    size_t padding = (bytes_transferred - register_size (gdbarch, regno));
-+    regcache_raw_supply (regcache, regno, buf + padding);
-+  }
-+  else
-+    internal_error (__FILE__, __LINE__,
-+                    _("fetch_register: unexpected byte order: %d"),
-+                    gdbarch_byte_order (gdbarch));
-+}
-+
-+/* This function actually issues the request to ptrace, telling
-+   it to get all general-purpose registers and put them into the
-+   specified regset.
-+
-+   If the ptrace request does not exist, this function returns 0
-+   and properly sets the have_ptrace_* flag.  If the request fails,
-+   this function calls perror_with_name.  Otherwise, if the request
-+   succeeds, then the regcache gets filled and 1 is returned.  */
-+static int
-+fetch_all_gp_regs (struct regcache *regcache, int tid)
-+{
-+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  gdb_gregset_t gregset;
-+
-+  if (ptrace (PTRACE_GETREGS, tid, 0, (void *) &gregset) < 0)
-+  {
-+    if (errno == EIO)
-+    {
-+      have_ptrace_getsetregs = 0;
-+      return 0;
-+    }
-+    perror_with_name (_("Couldn't get general-purpose registers."));
-+  }
-+
-+  supply_gregset (regcache, (const gdb_gregset_t *) &gregset);
-+
-+  return 1;
-+}
-+
-+
-+/* This is a wrapper for the fetch_all_gp_regs function.  It is
-+   responsible for verifying if this target has the ptrace request
-+   that can be used to fetch all general-purpose registers at one
-+   shot.  If it doesn't, then we should fetch them using the
-+   old-fashioned way, which is to iterate over the registers and
-+   request them one by one.  */
-+static void
-+fetch_gp_regs (struct regcache *regcache, int tid)
-+{
-+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  int i;
-+
-+  if (have_ptrace_getsetregs)
-+    if (fetch_all_gp_regs (regcache, tid))
-+      return;
-+
-+  /* If we've hit this point, it doesn't really matter which
-+     architecture we are using.  We just need to read the
-+     registers in the "old-fashioned way".  */
-+  for (i = MICROBLAZE_R0_REGNUM; i <= MICROBLAZE_FSR_REGNUM; i++)
-+    fetch_register (regcache, tid, i);
-+}
-+
-+
-+static void
-+store_register (const struct regcache *regcache, int tid, int regno)
-+{
-+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  /* This isn't really an address.  But ptrace thinks of it as one.  */
-+  CORE_ADDR regaddr = microblaze_register_u_addr (gdbarch, regno);
-+  int i;
-+  size_t bytes_to_transfer;
-+  char buf[MAX_REGISTER_SIZE];
-+
-+  if (regaddr == -1)
-+    return;
-+
-+  /* First collect the register.  Keep in mind that the regcache's
-+     idea of the register's size may not be a multiple of sizeof
-+     (long).  */
-+  memset (buf, 0, sizeof buf);
-+  bytes_to_transfer = align_up (register_size (gdbarch, regno), sizeof (long));
-+  if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_LITTLE)
-+  {
-+    /* Little-endian values always sit at the left end of the buffer.  */
-+    regcache_raw_collect (regcache, regno, buf);
-+  }
-+  else if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
-+  {
-+    /* Big-endian values sit at the right end of the buffer.  */
-+    size_t padding = (bytes_to_transfer - register_size (gdbarch, regno));
-+    regcache_raw_collect (regcache, regno, buf + padding);
-+  }
-+
-+  for (i = 0; i < bytes_to_transfer; i += sizeof (long))
-+  {
-+    long l;
-+
-+    memcpy (&l, &buf[i], sizeof (l));
-+    errno = 0;
-+    ptrace (PTRACE_POKEUSER, tid, (PTRACE_TYPE_ARG3) regaddr, l);
-+    regaddr += sizeof (long);
-+
-+    if (errno != 0)
-+    {
-+      char message[128];
-+      sprintf (message, "writing register %s (#%d)",
-+               gdbarch_register_name (gdbarch, regno), regno);
-+      perror_with_name (message);
-+    }
-+  }
-+}
-+
-+/* This function actually issues the request to ptrace, telling
-+   it to store all general-purpose registers present in the specified
-+   regset.
-+
-+   If the ptrace request does not exist, this function returns 0
-+   and properly sets the have_ptrace_* flag.  If the request fails,
-+   this function calls perror_with_name.  Otherwise, if the request
-+   succeeds, then the regcache is stored and 1 is returned.  */
-+static int
-+store_all_gp_regs (const struct regcache *regcache, int tid, int regno)
-+{
-+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  gdb_gregset_t gregset;
-+
-+  if (ptrace (PTRACE_GETREGS, tid, 0, (void *) &gregset) < 0)
-+    {
-+      if (errno == EIO)
-+      {
-+        have_ptrace_getsetregs = 0;
-+        return 0;
-+      }
-+      perror_with_name (_("Couldn't get general-purpose registers."));
-+    }
-+
-+  fill_gregset (regcache, &gregset, regno);
-+
-+  if (ptrace (PTRACE_SETREGS, tid, 0, (void *) &gregset) < 0)
-+    {
-+      if (errno == EIO)
-+      {
-+        have_ptrace_getsetregs = 0;
-+        return 0;
-+      }
-+      perror_with_name (_("Couldn't set general-purpose registers."));
-+    }
-+
-+  return 1;
-+}
-+
-+/* This is a wrapper for the store_all_gp_regs function.  It is
-+   responsible for verifying if this target has the ptrace request
-+   that can be used to store all general-purpose registers at one
-+   shot.  If it doesn't, then we should store them using the
-+   old-fashioned way, which is to iterate over the registers and
-+   store them one by one.  */
-+static void
-+store_gp_regs (const struct regcache *regcache, int tid, int regno)
-+{
-+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+  int i;
-+
-+  if (have_ptrace_getsetregs)
-+    if (store_all_gp_regs (regcache, tid, regno))
-+      return;
-+
-+  /* If we hit this point, it doesn't really matter which
-+     architecture we are using.  We just need to store the
-+     registers in the "old-fashioned way".  */
-+  for (i = MICROBLAZE_R0_REGNUM; i <= MICROBLAZE_FSR_REGNUM; i++)
-+    store_register (regcache, tid, i);
-+}
-+
-+
-+/* Fetch registers from the child process.  Fetch all registers if
-+   regno == -1, otherwise fetch all general registers or all floating
-+   point registers depending upon the value of regno.  */
-+
-+static void
-+microblaze_linux_fetch_inferior_registers (struct target_ops *ops,
-+				    struct regcache *regcache, int regno)
-+{
-+  /* Get the thread id for the ptrace call.  */
-+  int tid = GET_THREAD_ID (inferior_ptid);
-+
-+  if (regno == -1)
-+    fetch_gp_regs (regcache, tid);
-+  else
-+    fetch_register (regcache, tid, regno);
-+}
-+
-+/* Store registers back into the inferior.  Store all registers if
-+   regno == -1, otherwise store all general registers or all floating
-+   point registers depending upon the value of regno.  */
-+
-+static void
-+microblaze_linux_store_inferior_registers (struct target_ops *ops,
-+				    struct regcache *regcache, int regno)
-+{
-+  /* Get the thread id for the ptrace call.  */
-+  int tid = GET_THREAD_ID (inferior_ptid);
-+
-+  if (regno >= 0)
-+    store_register (regcache, tid, regno);
-+  else
-+    store_gp_regs (regcache, tid, -1);
-+}
-+
-+/* Wrapper functions for the standard regset handling, used by
-+   thread debugging.  */
-+
-+void
-+fill_gregset (const struct regcache *regcache,
-+	      gdb_gregset_t *gregsetp, int regno)
-+{
-+  microblaze_collect_gregset (NULL, regcache, regno, gregsetp);
-+}
-+
-+void
-+supply_gregset (struct regcache *regcache, const gdb_gregset_t *gregsetp)
-+{
-+  microblaze_supply_gregset (NULL, regcache, -1, gregsetp);
-+}
-+
-+void
-+fill_fpregset (const struct regcache *regcache,
-+	      gdb_fpregset_t *fpregsetp, int regno)
-+{
-+  /* FIXME. */
-+}
-+
-+void
-+supply_fpregset (struct regcache *regcache, const gdb_fpregset_t *fpregsetp)
-+{
-+  /* FIXME. */
-+}
-+
-+static const struct target_desc *
-+microblaze_linux_read_description (struct target_ops *ops)
-+{
-+  CORE_ADDR microblaze_hwcap = 0;
-+
-+  if (target_auxv_search (ops, AT_HWCAP, &microblaze_hwcap) != 1)
-+    return NULL;
-+
-+  return NULL;
-+}
-+
-+
-+void _initialize_microblaze_linux_nat (void);
-+
-+void
-+_initialize_microblaze_linux_nat (void)
-+{
-+  struct target_ops *t;
-+
-+  /* Fill in the generic GNU/Linux methods.  */
-+  t = linux_target ();
-+
-+  /* Add our register access methods.  */
-+  t->to_fetch_registers = microblaze_linux_fetch_inferior_registers;
-+  t->to_store_registers = microblaze_linux_store_inferior_registers;
-+
-+  t->to_read_description = microblaze_linux_read_description;
-+
-+  /* Register the target.  */
-+  linux_nat_add_target (t);
-+}
-diff -Nur gdb-7.8.2.orig/gdb/microblaze-linux-tdep.c gdb-7.8.2/gdb/microblaze-linux-tdep.c
---- gdb-7.8.2.orig/gdb/microblaze-linux-tdep.c	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/microblaze-linux-tdep.c	2016-05-15 13:56:18.171253048 +0200
-@@ -1,6 +1,6 @@
- /* Target-dependent code for Xilinx MicroBlaze.
- 
--   Copyright (C) 2009-2014 Free Software Foundation, Inc.
-+   Copyright (C) 2009-2013 Free Software Foundation, Inc.
- 
-    This file is part of GDB.
- 
-@@ -32,11 +32,28 @@
- #include "regset.h"
- #include "solib-svr4.h"
- #include "microblaze-tdep.h"
-+#include "glibc-tdep.h"
- #include "trad-frame.h"
- #include "frame-unwind.h"
- #include "tramp-frame.h"
- #include "linux-tdep.h"
- 
-+static int microblaze_debug_flag = 0;
-+
-+static void
-+microblaze_debug (const char *fmt, ...)
-+{
-+  if (microblaze_debug_flag)
-+    {
-+       va_list args;
-+
-+       va_start (args, fmt);
-+       printf_unfiltered ("MICROBLAZE LINUX: ");
-+       vprintf_unfiltered (fmt, args);
-+       va_end (args);
-+    }
-+}
-+
- static int
- microblaze_linux_memory_remove_breakpoint (struct gdbarch *gdbarch, 
- 					   struct bp_target_info *bp_tgt)
-@@ -46,20 +63,27 @@
-   int val;
-   int bplen;
-   gdb_byte old_contents[BREAKPOINT_MAX];
-+  struct cleanup *cleanup;
- 
-   /* Determine appropriate breakpoint contents and size for this address.  */
-   bp = gdbarch_breakpoint_from_pc (gdbarch, &addr, &bplen);
-   if (bp == NULL)
-     error (_("Software breakpoints not implemented for this target."));
- 
-+  /* Make sure we see the memory breakpoints.  */
-+  cleanup = make_show_memory_breakpoints_cleanup (1);
-   val = target_read_memory (addr, old_contents, bplen);
- 
-   /* If our breakpoint is no longer at the address, this means that the
-      program modified the code on us, so it is wrong to put back the
-      old value.  */
-   if (val == 0 && memcmp (bp, old_contents, bplen) == 0)
--    val = target_write_raw_memory (addr, bp_tgt->shadow_contents, bplen);
-+  {
-+      val = target_write_raw_memory (addr, bp_tgt->shadow_contents, bplen);
-+      microblaze_debug ("microblaze_linux_memory_remove_breakpoint writing back to memory at addr 0x%lx\n", addr);
-+  }
- 
-+  do_cleanups (cleanup);
-   return val;
- }
- 
-@@ -116,6 +140,50 @@
-   microblaze_linux_sighandler_cache_init
- };
- 
-+const struct microblaze_gregset microblaze_linux_core_gregset;
-+
-+static void
-+microblaze_linux_supply_core_gregset (const struct regset *regset,
-+                                   struct regcache *regcache,
-+                                   int regnum, const void *gregs, size_t len)
-+{
-+  microblaze_supply_gregset (&microblaze_linux_core_gregset, regcache,
-+                             regnum, gregs);
-+}
-+
-+static void
-+microblaze_linux_collect_core_gregset (const struct regset *regset,
-+                                    const struct regcache *regcache,
-+                                    int regnum, void *gregs, size_t len)
-+{
-+  microblaze_collect_gregset (&microblaze_linux_core_gregset, regcache,
-+                              regnum, gregs);
-+}
-+
-+static void
-+microblaze_linux_supply_core_fpregset (const struct regset *regset,
-+                                    struct regcache *regcache,
-+                                    int regnum, const void *fpregs, size_t len)
-+{
-+  /* FIXME.  */
-+  microblaze_supply_fpregset (regcache, regnum, fpregs);
-+}
-+
-+static void
-+microblaze_linux_collect_core_fpregset (const struct regset *regset,
-+                                     const struct regcache *regcache,
-+                                     int regnum, void *fpregs, size_t len)
-+{
-+  /* FIXME.  */
-+  microblaze_collect_fpregset (regcache, regnum, fpregs);
-+}
-+
-+static const struct regset microblaze_linux_gregset =
-+{
-+    NULL,
-+    microblaze_linux_supply_core_gregset,
-+    microblaze_linux_collect_core_gregset
-+};
- 
- static void
- microblaze_linux_init_abi (struct gdbarch_info info,
-@@ -123,6 +191,9 @@
- {
-   struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
- 
-+  tdep->gregset = &microblaze_linux_gregset;
-+  tdep->sizeof_gregset = 200;
-+
-   linux_init_abi (info, gdbarch);
- 
-   set_gdbarch_memory_remove_breakpoint (gdbarch,
-@@ -135,6 +206,25 @@
-   /* Trampolines.  */
-   tramp_frame_prepend_unwinder (gdbarch,
- 				&microblaze_linux_sighandler_tramp_frame);
-+
-+  /* BFD target for core files.  */
-+  if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
-+    set_gdbarch_gcore_bfd_target (gdbarch, "elf32-microblaze");
-+  else
-+    set_gdbarch_gcore_bfd_target (gdbarch, "elf32-microblazeel");
-+
-+
-+  /* Shared library handling.  */
-+  set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target);
-+  set_gdbarch_skip_solib_resolver (gdbarch, glibc_skip_solib_resolver);
-+
-+  set_gdbarch_regset_from_core_section (gdbarch,
-+					microblaze_regset_from_core_section);
-+
-+  /* Enable TLS support.  */
-+  set_gdbarch_fetch_tls_load_module_address (gdbarch,
-+                                             svr4_fetch_objfile_link_map);
-+
- }
- 
- /* -Wmissing-prototypes */
-diff -Nur gdb-7.8.2.orig/gdb/microblaze-rom.c gdb-7.8.2/gdb/microblaze-rom.c
---- gdb-7.8.2.orig/gdb/microblaze-rom.c	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/microblaze-rom.c	2016-05-14 21:29:38.997383530 +0200
-@@ -1,6 +1,6 @@
- /* Remote debugging interface to Xilinx MicroBlaze.
- 
--   Copyright (C) 2009-2014 Free Software Foundation, Inc.
-+   Copyright (C) 2009-2013 Free Software Foundation, Inc.
- 
-    This file is part of GDB.
- 
-@@ -21,7 +21,6 @@
- #include "gdbcore.h"
- #include "target.h"
- #include "monitor.h"
--#include <string.h>
- #include "serial.h"
- #include "regcache.h"
- 
-diff -Nur gdb-7.8.2.orig/gdb/microblaze-tdep.c gdb-7.8.2/gdb/microblaze-tdep.c
---- gdb-7.8.2.orig/gdb/microblaze-tdep.c	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/microblaze-tdep.c	2016-05-14 21:29:38.997383530 +0200
-@@ -1,6 +1,6 @@
- /* Target-dependent code for Xilinx MicroBlaze.
- 
--   Copyright (C) 2009-2014 Free Software Foundation, Inc.
-+   Copyright (C) 2009-2013 Free Software Foundation, Inc.
- 
-    This file is part of GDB.
- 
-@@ -29,13 +29,13 @@
- #include "inferior.h"
- #include "regcache.h"
- #include "target.h"
-+#include "frame.h"
- #include "frame-base.h"
- #include "frame-unwind.h"
- #include "dwarf2-frame.h"
- #include "osabi.h"
- 
- #include "gdb_assert.h"
--#include <string.h>
- #include "target-descriptions.h"
- #include "opcodes/microblaze-opcm.h"
- #include "opcodes/microblaze-dis.h"
-@@ -73,7 +73,8 @@
-   "rpc",  "rmsr", "rear", "resr", "rfsr", "rbtr",
-   "rpvr0", "rpvr1", "rpvr2", "rpvr3", "rpvr4", "rpvr5", "rpvr6",
-   "rpvr7", "rpvr8", "rpvr9", "rpvr10", "rpvr11",
--  "redr", "rpid", "rzpr", "rtlbx", "rtlbsx", "rtlblo", "rtlbhi"
-+  "redr", "rpid", "rzpr", "rtlbx", "rtlbsx", "rtlblo", "rtlbhi",
-+  "rslr", "rshr"
- };
- 
- #define MICROBLAZE_NUM_REGS ARRAY_SIZE (microblaze_register_names)
-@@ -145,6 +146,14 @@
-   return sp;
- }
- 
-+static CORE_ADDR
-+microblaze_store_arguments (struct regcache *regcache, int nargs,
-+			    struct value **args, CORE_ADDR sp,
-+			    int struct_return, CORE_ADDR struct_addr)
-+{
-+  error (_("store_arguments not implemented"));
-+  return sp;
-+}
- 
- static CORE_ADDR
- microblaze_push_dummy_call (struct gdbarch *gdbarch, struct value *function,
-@@ -156,14 +165,52 @@
-   return sp;
- }
- 
-+static int
-+microblaze_linux_memory_remove_breakpoint (struct gdbarch *gdbarch,
-+				    struct bp_target_info *bp_tgt)
-+{
-+  CORE_ADDR addr = bp_tgt->placed_address;
-+  const unsigned char *bp;
-+  int val;
-+  int bplen;
-+  gdb_byte old_contents[BREAKPOINT_MAX];
-+  struct cleanup *cleanup;
-+
-+  /* Determine appropriate breakpoint contents and size for this address.  */
-+  bp = gdbarch_breakpoint_from_pc (gdbarch, &addr, &bplen);
-+  if (bp == NULL)
-+    error (_("Software breakpoints not implemented for this target."));
-+
-+  /* Make sure we see the memory breakpoints.  */
-+  cleanup = make_show_memory_breakpoints_cleanup (1);
-+  val = target_read_memory (addr, old_contents, bplen);
-+
-+  /* If our breakpoint is no longer at the address, this means that the
-+     program modified the code on us, so it is wrong to put back the
-+     old value.  */
-+  if (val == 0 && memcmp (bp, old_contents, bplen) == 0)
-+  {
-+    val = target_write_raw_memory (addr, bp_tgt->shadow_contents, bplen);
-+    microblaze_debug ("microblaze_linux_memory_remove_breakpoint writing back to memory at addr 0x%lx\n", addr);
-+  }
-+
-+  do_cleanups (cleanup);
-+  return val;
-+}
-+
- static const gdb_byte *
- microblaze_breakpoint_from_pc (struct gdbarch *gdbarch, CORE_ADDR *pc, 
- 			       int *len)
- {
-+  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
-   static gdb_byte break_insn[] = MICROBLAZE_BREAKPOINT;
-+  static gdb_byte break_insn_le[] = MICROBLAZE_BREAKPOINT_LE;
- 
-   *len = sizeof (break_insn);
--  return break_insn;
-+  if (byte_order == BFD_ENDIAN_BIG)
-+    return break_insn;
-+  else
-+    return break_insn_le;
- }
- 
- /* Allocate and initialize a frame cache.  */
-@@ -178,6 +225,7 @@
-   /* Base address.  */
-   cache->base = 0;
-   cache->pc = 0;
-+  cache->saved_sp = 0;
- 
-   /* Frameless until proven otherwise.  */
-   cache->frameless_p = 1;
-@@ -234,6 +282,8 @@
-   int flags = 0;
-   int save_hidden_pointer_found = 0;
-   int non_stack_instruction_found = 0;
-+  int n_insns;
-+  unsigned int *insn_block;
- 
-   /* Find the start of this function.  */
-   find_pc_partial_function (pc, &name, &func_addr, &func_end);
-@@ -273,11 +323,18 @@
- 		    name, paddress (gdbarch, func_addr), 
- 		    paddress (gdbarch, stop));
- 
-+/* Do a block read to minimize the transaction with the Debug Agent */
-+  n_insns = (stop == func_addr) ? 1 : ((stop - func_addr) / INST_WORD_SIZE);
-+  insn_block = calloc(n_insns, sizeof(unsigned long));
-+
-+  target_read_memory (func_addr, (void*) insn_block, n_insns * INST_WORD_SIZE );
-+
-   for (addr = func_addr; addr < stop; addr += INST_WORD_SIZE)
-     {
-       insn = microblaze_fetch_instruction (addr);
-+      //insn = insn_block[(addr - func_addr) / INST_WORD_SIZE];
-       op = microblaze_decode_insn (insn, &rd, &ra, &rb, &imm);
--      microblaze_debug ("%s %08lx\n", paddress (gdbarch, pc), insn);
-+      microblaze_debug ("%s %08lx op=%x r%d r%d imm=%d\n", paddress (gdbarch, addr), insn, op, rd, ra, imm);
- 
-       /* This code is very sensitive to what functions are present in the
- 	 prologue.  It assumes that the (addi, addik, swi, sw) can be the 
-@@ -291,6 +348,7 @@
- 	  cache->frameless_p = 0; /* Frame found.  */
- 	  save_hidden_pointer_found = 0;
- 	  non_stack_instruction_found = 0;
-+	  cache->register_offsets[rd] = -imm;
- 	  continue;
- 	}
-       else if (IS_SPILL_SP(op, rd, ra))
-@@ -401,8 +459,8 @@
-      part of the prologue.  */
-   if (save_hidden_pointer_found)
-     prologue_end_addr -= INST_WORD_SIZE;
--
--  return prologue_end_addr;
-+    free(insn_block);
-+    return prologue_end_addr;
- }
- 
- static CORE_ADDR
-@@ -452,6 +510,7 @@
-   return start_pc;
- }
- 
-+enum { REG_UNAVAIL = (CORE_ADDR) -1 };
- /* Normal frames.  */
- 
- static struct microblaze_frame_cache *
-@@ -459,7 +518,7 @@
- {
-   struct microblaze_frame_cache *cache;
-   struct gdbarch *gdbarch = get_frame_arch (next_frame);
--  CORE_ADDR func;
-+  CORE_ADDR current_pc;
-   int rn;
- 
-   if (*this_cache)
-@@ -473,9 +532,18 @@
-   for (rn = 0; rn < gdbarch_num_regs (gdbarch); rn++)
-     cache->register_offsets[rn] = -1;
- 
--  func = get_frame_func (next_frame);
-+  cache->pc = get_frame_func (next_frame);
-+  current_pc = get_frame_pc (next_frame);
-+
-+  if (cache->pc)
-+    microblaze_analyze_prologue (gdbarch, cache->pc, current_pc,
-+	                         cache);
-+
-+  cache->base = get_frame_register_unsigned (next_frame, gdbarch_sp_regnum (gdbarch));
-+  cache->saved_sp = cache->base + cache->framesize;
- 
--  cache->pc = get_frame_address_in_block (next_frame);
-+  cache->register_offsets[MICROBLAZE_PREV_PC_REGNUM] = cache->base;
-+  cache->register_offsets[MICROBLAZE_SP_REGNUM] = cache->saved_sp;
- 
-   return cache;
- }
-@@ -501,6 +569,14 @@
-   struct microblaze_frame_cache *cache =
-     microblaze_frame_cache (this_frame, this_cache);
- 
-+  if ((regnum == MICROBLAZE_SP_REGNUM &&
-+      cache->register_offsets[MICROBLAZE_SP_REGNUM])
-+      || (regnum == MICROBLAZE_FP_REGNUM &&
-+      cache->register_offsets[MICROBLAZE_SP_REGNUM]))
-+
-+     return frame_unwind_got_constant (this_frame, regnum,
-+                                       cache->register_offsets[MICROBLAZE_SP_REGNUM]);
-+
-   if (cache->frameless_p)
-     {
-       if (regnum == MICROBLAZE_PC_REGNUM)
-@@ -508,11 +584,18 @@
-       if (regnum == MICROBLAZE_SP_REGNUM)
-         regnum = 1;
-       return trad_frame_get_prev_register (this_frame,
--					   cache->saved_regs, regnum);
-+            cache->saved_regs, regnum);
-     }
--  else
--    return trad_frame_get_prev_register (this_frame, cache->saved_regs,
--					 regnum);
-+
-+  if (regnum == MICROBLAZE_PC_REGNUM)
-+    {
-+      regnum = 15;
-+      return frame_unwind_got_memory (this_frame, regnum,
-+                                      cache->register_offsets[MICROBLAZE_PREV_PC_REGNUM]);
-+    }
-+
-+  return trad_frame_get_prev_register (this_frame, cache->saved_regs,
-+					regnum);
- 
- }
- 
-@@ -536,6 +619,12 @@
-   return cache->base;
- }
- 
-+static const struct frame_unwind *
-+microblaze_frame_sniffer (struct frame_info *next_frame)
-+{
-+  return &microblaze_frame_unwind;
-+}
-+
- static const struct frame_base microblaze_frame_base =
- {
-   &microblaze_frame_unwind,
-@@ -628,6 +717,109 @@
-   return (TYPE_LENGTH (type) == 16);
- }
- 
-+int
-+microblaze_software_single_step (struct frame_info *frame)
-+{
-+  struct gdbarch *arch = get_frame_arch (frame);
-+  struct address_space *aspace = get_frame_address_space (frame);
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (arch);
-+  static char le_breakp[] = MICROBLAZE_BREAKPOINT_LE;
-+  static char be_breakp[] = MICROBLAZE_BREAKPOINT;
-+  enum bfd_endian byte_order = gdbarch_byte_order (arch);
-+  char *breakp = byte_order == BFD_ENDIAN_BIG ? be_breakp : le_breakp;
-+  int ret = 0;
-+
-+  /* Save the address and the values of the next_pc and the target */
-+  static struct sstep_breaks
-+  {
-+    CORE_ADDR address;
-+    bfd_boolean valid;
-+    /* Shadow contents.  */
-+    char data[INST_WORD_SIZE];
-+  } stepbreaks[2];
-+  int ii;
-+
-+  if (1)
-+    {
-+      CORE_ADDR pc;
-+      long insn;
-+      enum microblaze_instr minstr;
-+      bfd_boolean isunsignednum;
-+      enum microblaze_instr_type insn_type;
-+      short delay_slots;
-+      int imm;
-+      bfd_boolean immfound = FALSE;
-+
-+      /* Set a breakpoint at the next instruction */
-+      /* If the current instruction is an imm, set it at the inst after */
-+      /* If the instruction has a delay slot, skip the delay slot */
-+      pc = get_frame_pc (frame);
-+      insn = microblaze_fetch_instruction (pc);
-+      minstr = get_insn_microblaze (insn, &isunsignednum, &insn_type, &delay_slots);
-+      if (insn_type == immediate_inst)
-+	{
-+	  int rd, ra, rb;
-+	  immfound = TRUE;
-+	  minstr = microblaze_decode_insn (insn, &rd, &ra, &rb, &imm);
-+	  pc = pc + INST_WORD_SIZE;
-+	  insn = microblaze_fetch_instruction (pc);
-+	  minstr = get_insn_microblaze (insn, &isunsignednum, &insn_type, &delay_slots);
-+	}
-+      stepbreaks[0].address = pc + (delay_slots * INST_WORD_SIZE) + INST_WORD_SIZE;
-+      if (insn_type != return_inst) {
-+	stepbreaks[0].valid = TRUE;
-+      } else {
-+	stepbreaks[0].valid = FALSE;
-+      }
-+
-+      microblaze_debug ("single-step insn_type=%x insn=%x\n", insn_type, insn);
-+      /* Now check for branch or return instructions */
-+      if (insn_type == branch_inst || insn_type == return_inst) {
-+	int limm;
-+	int lrd, lra, lrb;
-+	int ra, rb;
-+	bfd_boolean targetvalid;
-+	bfd_boolean unconditionalbranch;
-+	microblaze_decode_insn(insn, &lrd, &lra, &lrb, &limm);
-+	if (lra >= 0 && lra < MICROBLAZE_NUM_REGS)
-+	  ra = get_frame_register_unsigned (frame, lra);
-+	else
-+	  ra = 0;
-+	if (lrb >= 0 && lrb < MICROBLAZE_NUM_REGS)
-+	  rb = get_frame_register_unsigned (frame, lrb);
-+	else
-+	  rb = 0;
-+
-+	stepbreaks[1].address = microblaze_get_target_address (insn, immfound, imm, pc, ra, rb, &targetvalid, &unconditionalbranch);
-+	microblaze_debug ("single-step uncondbr=%d targetvalid=%d target=%x\n", unconditionalbranch, targetvalid, stepbreaks[1].address);
-+
-+	if (unconditionalbranch)
-+	  stepbreaks[0].valid = FALSE; /* This is a unconditional branch: will not come to the next address */
-+	if (targetvalid && (stepbreaks[0].valid == FALSE ||
-+			    (stepbreaks[0].address != stepbreaks[1].address))
-+			&& (stepbreaks[1].address != pc)) {
-+	  stepbreaks[1].valid = TRUE;
-+	} else {
-+	  stepbreaks[1].valid = FALSE;
-+	}
-+      } else {
-+	stepbreaks[1].valid = FALSE;
-+      }
-+
-+      /* Insert the breakpoints */
-+      for (ii = 0; ii < 2; ++ii)
-+        {
-+
-+          /* ignore invalid breakpoint. */
-+          if (stepbreaks[ii].valid) {
-+            insert_single_step_breakpoint (arch, aspace, stepbreaks[ii].address);
-+            ret = 1;
-+	  }
-+	}
-+    }
-+    return ret;
-+}
-+
- static void
- microblaze_write_pc (struct regcache *regcache, CORE_ADDR pc)
- {
-@@ -664,6 +856,70 @@
-   return dwarf2_to_reg_map[reg];
- }
- 
-+
-+void
-+microblaze_supply_gregset (const struct microblaze_gregset *gregset,
-+                        struct regcache *regcache,
-+                        int regnum, const void *gregs)
-+{
-+  unsigned int *regs = gregs;
-+  if (regnum >= 0)
-+    regcache_raw_supply (regcache, regnum, regs + regnum);
-+
-+  if (regnum == -1) {
-+    int i;
-+
-+    for (i = 0; i < 50; i++) {
-+      regcache_raw_supply (regcache, i, regs + i);
-+    }
-+  }
-+}
-+
-+
-+void
-+microblaze_collect_gregset (const struct microblaze_gregset *gregset,
-+                         const struct regcache *regcache,
-+                         int regnum, void *gregs)
-+{
-+   /* FIXME.  */
-+}
-+
-+void
-+microblaze_supply_fpregset (struct regcache *regcache,
-+                         int regnum, const void *fpregs)
-+{
-+   /* FIXME.  */
-+}
-+
-+void
-+microblaze_collect_fpregset (const struct regcache *regcache,
-+                          int regnum, void *fpregs)
-+{
-+   /* FIXME.  */
-+}
-+
-+
-+/* Return the appropriate register set for the core section identified
-+   by SECT_NAME and SECT_SIZE.  */
-+
-+const struct regset *
-+microblaze_regset_from_core_section (struct gdbarch *gdbarch,
-+                                     const char *sect_name, size_t sect_size)
-+{
-+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-+
-+  microblaze_debug ("microblaze_regset_from_core_section, sect_name = %s\n", sect_name);
-+
-+  if (strcmp (sect_name, ".reg") == 0 && sect_size >= tdep->sizeof_gregset)
-+    return tdep->gregset;
-+
-+  if (strcmp (sect_name, ".reg2") == 0 && sect_size >= tdep->sizeof_fpregset)
-+    return tdep->fpregset;
-+
-+  microblaze_debug ("microblaze_regset_from_core_section returning null :-( \n");
-+  return NULL;
-+}
-+
- static struct gdbarch *
- microblaze_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
- {
-@@ -679,6 +935,11 @@
-   tdep = XNEW (struct gdbarch_tdep);
-   gdbarch = gdbarch_alloc (&info, tdep);
- 
-+  tdep->gregset = NULL;
-+  tdep->sizeof_gregset = 0;
-+  tdep->fpregset = NULL;
-+  tdep->sizeof_fpregset = 0;
-+
-   set_gdbarch_long_double_bit (gdbarch, 128);
- 
-   set_gdbarch_num_regs (gdbarch, MICROBLAZE_NUM_REGS);
-@@ -706,7 +967,10 @@
-   /* Stack grows downward.  */
-   set_gdbarch_inner_than (gdbarch, core_addr_lessthan);
- 
-+  set_gdbarch_memory_remove_breakpoint (gdbarch, microblaze_linux_memory_remove_breakpoint);
-+
-   set_gdbarch_breakpoint_from_pc (gdbarch, microblaze_breakpoint_from_pc);
-+  set_gdbarch_software_single_step (gdbarch, microblaze_software_single_step);
- 
-   set_gdbarch_frame_args_skip (gdbarch, 8);
- 
-@@ -725,6 +989,13 @@
-   dwarf2_append_unwinders (gdbarch);
-   frame_unwind_append_unwinder (gdbarch, &microblaze_frame_unwind);
-   frame_base_append_sniffer (gdbarch, dwarf2_frame_base_sniffer);
-+  //frame_base_append_sniffer (gdbarch, microblaze_frame_sniffer);
-+
-+  /* If we have register sets, enable the generic core file support.  */
-+  if (tdep->gregset) {
-+      set_gdbarch_regset_from_core_section (gdbarch,
-+                                          microblaze_regset_from_core_section);
-+  }
- 
-   return gdbarch;
- }
-diff -Nur gdb-7.8.2.orig/gdb/microblaze-tdep.h gdb-7.8.2/gdb/microblaze-tdep.h
---- gdb-7.8.2.orig/gdb/microblaze-tdep.h	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/gdb/microblaze-tdep.h	2016-05-14 21:29:38.997383530 +0200
-@@ -1,6 +1,6 @@
- /* Target-dependent code for Xilinx MicroBlaze.
- 
--   Copyright (C) 2009-2014 Free Software Foundation, Inc.
-+   Copyright (C) 2009-2013 Free Software Foundation, Inc.
- 
-    This file is part of GDB.
- 
-@@ -22,8 +22,22 @@
- 
- 
- /* Microblaze architecture-specific information.  */
-+struct microblaze_gregset
-+{
-+   unsigned int gregs[32];
-+   unsigned int fpregs[32];
-+   unsigned int pregs[16];
-+};
-+
- struct gdbarch_tdep
- {
-+  int dummy;		// declare something.
-+
-+  /* Register sets.  */
-+  struct regset *gregset;
-+  size_t sizeof_gregset;
-+  struct regset *fpregset;
-+  size_t sizeof_fpregset;
- };
- 
- struct microblaze_frame_cache
-@@ -42,7 +56,8 @@
-   int fp_regnum;
- 
-   /* Offsets to saved registers.  */
--  int register_offsets[57];	/* Must match MICROBLAZE_NUM_REGS.  */
-+  int register_offsets[59];	/* Must match MICROBLAZE_NUM_REGS.  */
-+  CORE_ADDR saved_sp;
- 
-   /* Table of saved registers.  */
-   struct trad_frame_saved_reg *saved_regs;
-@@ -66,11 +81,11 @@
-   MICROBLAZE_R12_REGNUM,
-   MICROBLAZE_R13_REGNUM,
-   MICROBLAZE_R14_REGNUM,
--  MICROBLAZE_R15_REGNUM,
-+  MICROBLAZE_R15_REGNUM, MICROBLAZE_PREV_PC_REGNUM = MICROBLAZE_R15_REGNUM,
-   MICROBLAZE_R16_REGNUM,
-   MICROBLAZE_R17_REGNUM,
-   MICROBLAZE_R18_REGNUM,
--  MICROBLAZE_R19_REGNUM,
-+  MICROBLAZE_R19_REGNUM, MICROBLAZE_FP_REGNUM = MICROBLAZE_R19_REGNUM,
-   MICROBLAZE_R20_REGNUM,
-   MICROBLAZE_R21_REGNUM,
-   MICROBLAZE_R22_REGNUM,
-@@ -107,7 +122,9 @@
-   MICROBLAZE_RTLBX_REGNUM,
-   MICROBLAZE_RTLBSX_REGNUM,
-   MICROBLAZE_RTLBLO_REGNUM,
--  MICROBLAZE_RTLBHI_REGNUM
-+  MICROBLAZE_RTLBHI_REGNUM,
-+  MICROBLAZE_SLR_REGNUM,
-+  MICROBLAZE_SHR_REGNUM
- };
- 
- /* All registers are 32 bits.  */
-@@ -115,6 +132,21 @@
- 
- /* MICROBLAZE_BREAKPOINT defines the breakpoint that should be used.
-    Only used for native debugging.  */
--#define MICROBLAZE_BREAKPOINT {0xb9, 0xcc, 0x00, 0x60}
-+#define MICROBLAZE_BREAKPOINT {0xba, 0x0c, 0x00, 0x18}
-+#define MICROBLAZE_BREAKPOINT_LE {0x18, 0x00, 0x0c, 0xba}
-+
-+extern void microblaze_supply_gregset (const struct microblaze_gregset *gregset,
-+                                    struct regcache *regcache,
-+                                    int regnum, const void *gregs);
-+extern void microblaze_collect_gregset (const struct microblaze_gregset *gregset,
-+                                     const struct regcache *regcache,
-+                                     int regnum, void *gregs);
-+extern void microblaze_supply_fpregset (struct regcache *regcache,
-+                                     int regnum, const void *fpregs);
-+extern void microblaze_collect_fpregset (const struct regcache *regcache,
-+                                      int regnum, void *fpregs);
-+
-+extern const struct regset * microblaze_regset_from_core_section (struct gdbarch *gdbarch,
-+                                     const char *sect_name, size_t sect_size);
- 
- #endif /* microblaze-tdep.h */
-diff -Nur gdb-7.8.2.orig/gdb/regformats/reg-microblaze.dat gdb-7.8.2/gdb/regformats/reg-microblaze.dat
---- gdb-7.8.2.orig/gdb/regformats/reg-microblaze.dat	1970-01-01 01:00:00.000000000 +0100
-+++ gdb-7.8.2/gdb/regformats/reg-microblaze.dat	2016-05-14 21:29:38.997383530 +0200
-@@ -0,0 +1,41 @@
-+name:microblaze
-+expedite:r1,pc
-+32:r0
-+32:r1
-+32:r2
-+32:r3
-+32:r4
-+32:r5
-+32:r6
-+32:r7
-+32:r8
-+32:r9
-+32:r10
-+32:r11
-+32:r12
-+32:r13
-+32:r14
-+32:r15
-+32:r16
-+32:r17
-+32:r18
-+32:r19
-+32:r20
-+32:r21
-+32:r22
-+32:r23
-+32:r24
-+32:r25
-+32:r26
-+32:r27
-+32:r28
-+32:r29
-+32:r30
-+32:r31
-+32:pc
-+32:msr
-+32:ear
-+32:esr
-+32:fsr
-+32:slr
-+32:shr
-diff -Nur gdb-7.8.2.orig/include/elf/microblaze.h gdb-7.8.2/include/elf/microblaze.h
---- gdb-7.8.2.orig/include/elf/microblaze.h	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/include/elf/microblaze.h	2016-05-14 21:29:38.997383530 +0200
-@@ -58,6 +58,7 @@
-   RELOC_NUMBER (R_MICROBLAZE_TLSDTPREL64, 27)   /* TLS Offset Within TLS Block */
-   RELOC_NUMBER (R_MICROBLAZE_TLSGOTTPREL32, 28) /* TLS Offset From Thread Pointer */
-   RELOC_NUMBER (R_MICROBLAZE_TLSTPREL32, 29)    /* TLS Offset From Thread Pointer */
-+  RELOC_NUMBER (R_MICROBLAZE_32_NONE, 30)
-    
- END_RELOC_NUMBERS (R_MICROBLAZE_max)
- 
-diff -Nur gdb-7.8.2.orig/opcodes/microblaze-opc.h gdb-7.8.2/opcodes/microblaze-opc.h
---- gdb-7.8.2.orig/opcodes/microblaze-opc.h	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/opcodes/microblaze-opc.h	2016-05-14 21:29:38.997383530 +0200
-@@ -91,6 +91,7 @@
- #define OPCODE_MASK_H3  0xFC000600  /* High 6 bits and bits 21, 22.  */  
- #define OPCODE_MASK_H32 0xFC00FC00  /* High 6 bits and bit 16-21.  */
- #define OPCODE_MASK_H34B 0xFC0000FF /* High 6 bits and low 8 bits.  */
-+#define OPCODE_MASK_H35B 0xFC0004FF /* High 6 bits and low 9 bits.  */
- #define OPCODE_MASK_H34C 0xFC0007E0 /* High 6 bits and bits 21-26.  */
- 
- /* New Mask for msrset, msrclr insns.  */
-@@ -101,7 +102,7 @@
- #define DELAY_SLOT 1
- #define NO_DELAY_SLOT 0
- 
--#define MAX_OPCODES 289
-+#define MAX_OPCODES 291
- 
- struct op_code_struct
- {
-@@ -174,7 +175,9 @@
-   {"wic",   INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000068, OPCODE_MASK_H34B, wic, special_inst },
-   {"wdc",   INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000064, OPCODE_MASK_H34B, wdc, special_inst },
-   {"wdc.clear", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000066, OPCODE_MASK_H34B, wdcclear, special_inst },
-+  {"wdc.ext.clear", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000466, OPCODE_MASK_H35B, wdcextclear, special_inst },
-   {"wdc.flush", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000074, OPCODE_MASK_H34B, wdcflush, special_inst },
-+  {"wdc.ext.flush", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000476, OPCODE_MASK_H35B, wdcextflush, special_inst },
-   {"mts",   INST_TYPE_SPECIAL_R1, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_MTS, 0x9400C000, OPCODE_MASK_H13S, mts, special_inst },
-   {"mfs",   INST_TYPE_RD_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_MFS, 0x94008000, OPCODE_MASK_H23S, mfs, special_inst },
-   {"br",    INST_TYPE_R2, INST_PC_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x98000000, OPCODE_MASK_H124, br, branch_inst },
-diff -Nur gdb-7.8.2.orig/opcodes/microblaze-opcm.h gdb-7.8.2/opcodes/microblaze-opcm.h
---- gdb-7.8.2.orig/opcodes/microblaze-opcm.h	2015-01-15 11:58:12.000000000 +0100
-+++ gdb-7.8.2/opcodes/microblaze-opcm.h	2016-05-14 21:29:38.997383530 +0200
-@@ -31,9 +31,9 @@
-   idiv, idivu, bsll, bsra, bsrl, get, put, nget, nput, cget, cput,
-   ncget, ncput, muli, bslli, bsrai, bsrli, mului, or, and, xor,
-   andn, pcmpbf, pcmpbc, pcmpeq, pcmpne, sra, src, srl, sext8, sext16, 
--  wic, wdc, wdcclear, wdcflush, mts, mfs, mbar, br, brd,
--  brld, bra, brad, brald, microblaze_brk, beq, beqd, bne, bned, blt,
--  bltd, ble, bled, bgt, bgtd, bge, bged, ori, andi, xori, andni,
-+  wic, wdc, wdcclear, wdcextclear, wdcflush, wdcextflush, mts, mfs, mbar,
-+  br, brd, brld, bra, brad, brald, microblaze_brk, beq, beqd, bne, bned,
-+  blt, bltd, ble, bled, bgt, bgtd, bge, bged, ori, andi, xori, andni,
-   imm, rtsd, rtid, rtbd, rted, bri, brid, brlid, brai, braid, bralid,
-   brki, beqi, beqid, bnei, bneid, blti, bltid, blei, bleid, bgti,
-   bgtid, bgei, bgeid, lbu, lbur, lhu, lhur, lw, lwr, lwx, sb, sbr, sh, 

+ 14 - 0
package/gdb-microblaze/patches/patch-bfd_bfd-in2_h

@@ -0,0 +1,14 @@
+--- gdb-7.8.2.orig/bfd/bfd-in2.h	2015-01-15 11:58:11.000000000 +0100
++++ gdb-7.8.2/bfd/bfd-in2.h	2016-09-21 10:34:30.025222164 +0200
+@@ -5449,6 +5449,11 @@ value relative to the read-write small d
+ expressions of the form "Symbol Op Symbol"  */
+   BFD_RELOC_MICROBLAZE_32_SYM_OP_SYM,
+ 
++/* This is a 32 bit reloc that stores the 32 bit pc relative
++value in two words (with an imm instruction).  No relocation is 
++done here - only used for relaxing  */
++  BFD_RELOC_MICROBLAZE_32_NONE,
++
+ /* This is a 64 bit reloc that stores the 32 bit pc relative
+ value in two words (with an imm instruction).  No relocation is
+ done here - only used for relaxing  */

+ 202 - 0
package/gdb-microblaze/patches/patch-bfd_elf32-microblaze_c

@@ -0,0 +1,202 @@
+--- gdb-7.8.2.orig/bfd/elf32-microblaze.c	2015-01-15 11:58:11.000000000 +0100
++++ gdb-7.8.2/bfd/elf32-microblaze.c	2016-09-21 10:34:30.025222164 +0200
+@@ -177,6 +177,20 @@ static reloc_howto_type microblaze_elf_h
+           FALSE), 		/* PC relative offset?  */
+ 
+    /* This reloc does nothing.  Used for relaxation.  */
++   HOWTO (R_MICROBLAZE_32_NONE,	/* Type.  */
++          0,			/* Rightshift.  */
++          2,			/* Size (0 = byte, 1 = short, 2 = long).  */
++          32,			/* Bitsize.  */
++          TRUE,			/* PC_relative.  */
++          0,			/* Bitpos.  */
++          complain_overflow_bitfield,  /* Complain on overflow.  */
++          NULL,                  /* Special Function.  */
++          "R_MICROBLAZE_32_NONE",/* Name.  */
++          FALSE,		/* Partial Inplace.  */
++          0,			/* Source Mask.  */
++          0,			/* Dest Mask.  */
++          FALSE),		/* PC relative offset?  */
++
+    HOWTO (R_MICROBLAZE_64_NONE,	/* Type.  */
+           0,			/* Rightshift.  */
+           2,			/* Size (0 = byte, 1 = short, 2 = long).  */
+@@ -532,7 +546,10 @@ microblaze_elf_reloc_type_lookup (bfd *
+     case BFD_RELOC_NONE:
+       microblaze_reloc = R_MICROBLAZE_NONE;
+       break;
+-    case BFD_RELOC_MICROBLAZE_64_NONE:
++    case BFD_RELOC_MICROBLAZE_32_NONE:
++      microblaze_reloc = R_MICROBLAZE_32_NONE;
++      break;
++     case BFD_RELOC_MICROBLAZE_64_NONE:
+       microblaze_reloc = R_MICROBLAZE_64_NONE;
+       break;
+     case BFD_RELOC_32:
+@@ -668,6 +685,67 @@ microblaze_elf_is_local_label_name (bfd
+   return _bfd_elf_is_local_label_name (abfd, name);
+ }
+ 
++/* Support for core dump NOTE sections.  */
++static bfd_boolean
++microblaze_elf_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
++{
++  int offset;
++  unsigned int size;
++
++  switch (note->descsz)
++    {
++      default:
++        return FALSE;
++
++      case 228:         /* Linux/MicroBlaze */
++        /* pr_cursig */
++        elf_tdata (abfd)->core->signal = bfd_get_16 (abfd, note->descdata + 12);
++
++        /* pr_pid */
++        elf_tdata (abfd)->core->pid = bfd_get_32 (abfd, note->descdata + 24);
++
++        /* pr_reg */
++        offset = 72;
++        size = 50 * 4;
++
++        break;
++    }
++
++  /* Make a ".reg/999" section.  */
++  return _bfd_elfcore_make_pseudosection (abfd, ".reg",
++                                          size, note->descpos + offset);
++}
++
++static bfd_boolean
++microblaze_elf_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
++{
++  switch (note->descsz)
++    {
++      default:
++        return FALSE;
++
++      case 128:         /* Linux/MicroBlaze elf_prpsinfo */
++        elf_tdata (abfd)->core->program
++         = _bfd_elfcore_strndup (abfd, note->descdata + 32, 16);
++        elf_tdata (abfd)->core->command
++         = _bfd_elfcore_strndup (abfd, note->descdata + 48, 80);
++    }
++
++  /* Note that for some reason, a spurious space is tacked
++     onto the end of the args in some (at least one anyway)
++     implementations, so strip it off if it exists.  */
++
++  {
++    char *command = elf_tdata (abfd)->core->command;
++    int n = strlen (command);
++
++    if (0 < n && command[n - 1] == ' ')
++      command[n - 1] = '\0';
++  }
++
++  return TRUE;
++}
++
+ /* The microblaze linker (like many others) needs to keep track of
+    the number of relocs that it decides to copy as dynamic relocs in
+    check_relocs for each symbol. This is so that it can later discard
+@@ -1023,7 +1101,7 @@ microblaze_elf_relocate_section (bfd *ou
+ 	    {
+ 	      /* External symbol.  */
+ 	      bfd_boolean warned ATTRIBUTE_UNUSED;
+-	      bfd_boolean ignored ATTRIBUTE_UNUSED;
++	      bfd_boolean ignored;
+ 
+ 	      RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
+ 				       r_symndx, symtab_hdr, sym_hashes,
+@@ -1852,14 +1930,22 @@ microblaze_elf_relax_section (bfd *abfd,
+ 	        }
+ 	      break;
+ 	    case R_MICROBLAZE_NONE:
++	    case R_MICROBLAZE_32_NONE:
+ 	      {
+ 	        /* This was a PC-relative instruction that was
+  		   completely resolved.  */
+ 	        int sfix, efix;
++		unsigned int val;
+ 	        bfd_vma target_address;
+ 	        target_address = irel->r_addend + irel->r_offset;
+ 	        sfix = calc_fixup (irel->r_offset, 0, sec);
+ 	        efix = calc_fixup (target_address, 0, sec);
++
++                /* Validate the in-band val.  */
++                val = bfd_get_32 (abfd, contents + irel->r_offset);
++                if (val != irel->r_addend && ELF32_R_TYPE (irel->r_info) == R_MICROBLAZE_32_NONE) {
++                    fprintf(stderr, "%d: CORRUPT relax reloc %x %lx\n", __LINE__, val, irel->r_addend);
++                }
+ 	        irel->r_addend -= (efix - sfix);
+ 	        /* Should use HOWTO.  */
+ 	        microblaze_bfd_write_imm_value_32 (abfd, contents + irel->r_offset,
+@@ -1907,6 +1993,49 @@ microblaze_elf_relax_section (bfd *abfd,
+           irelscanend = irelocs + o->reloc_count;
+           for (irelscan = irelocs; irelscan < irelscanend; irelscan++)
+             {
++              if (1 && ELF32_R_TYPE (irelscan->r_info) == (int) R_MICROBLAZE_32_NONE)
++                {
++                  unsigned int val;
++
++                  isym = isymbuf + ELF32_R_SYM (irelscan->r_info);
++
++                  /* hax: We only do the following fixup for debug location lists.  */
++                  if (strcmp(".debug_loc", o->name))
++                    continue;
++
++                  /* This was a PC-relative instruction that was completely resolved.  */
++                  if (ocontents == NULL)
++                    {
++		      if (elf_section_data (o)->this_hdr.contents != NULL)
++		          ocontents = elf_section_data (o)->this_hdr.contents;
++		      else
++		        {
++		          /* We always cache the section contents.
++			     Perhaps, if info->keep_memory is FALSE, we
++			     should free them, if we are permitted to.  */
++
++		          if (o->rawsize == 0)
++			      o->rawsize = o->size;
++		          ocontents = (bfd_byte *) bfd_malloc (o->rawsize);
++		          if (ocontents == NULL)
++			      goto error_return;
++		          if (!bfd_get_section_contents (abfd, o, ocontents,
++                                                         (file_ptr) 0,
++                                                         o->rawsize))
++                              goto error_return;
++		          elf_section_data (o)->this_hdr.contents = ocontents;
++		        }
++		    }
++
++                  val = bfd_get_32 (abfd, ocontents + irelscan->r_offset);
++                  if (val != irelscan->r_addend) {
++			fprintf(stderr, "%d: CORRUPT relax reloc! %x %lx\n", __LINE__, val, irelscan->r_addend);
++                  }
++
++                  irelscan->r_addend -= calc_fixup (irelscan->r_addend, 0, sec);
++                  microblaze_bfd_write_imm_value_32 (abfd, ocontents + irelscan->r_offset,
++                                                     irelscan->r_addend);
++              }
+               if (ELF32_R_TYPE (irelscan->r_info) == (int) R_MICROBLAZE_32)
+                 {
+ 	          isym = isymbuf + ELF32_R_SYM (irelscan->r_info);
+@@ -1966,7 +2095,7 @@ microblaze_elf_relax_section (bfd *abfd,
+ 			      elf_section_data (o)->this_hdr.contents = ocontents;
+ 			    }
+ 			}
+-		      irelscan->r_addend -= calc_fixup (irel->r_addend
++		      irelscan->r_addend -= calc_fixup (irelscan->r_addend
+ 							+ isym->st_value,
+ 							0,
+ 							sec);
+@@ -3506,4 +3635,7 @@ microblaze_elf_add_symbol_hook (bfd *abf
+ #define elf_backend_size_dynamic_sections       microblaze_elf_size_dynamic_sections
+ #define elf_backend_add_symbol_hook		microblaze_elf_add_symbol_hook
+ 
++#define elf_backend_grok_prstatus               microblaze_elf_grok_prstatus
++#define elf_backend_grok_psinfo                 microblaze_elf_grok_psinfo
++
+ #include "elf32-target.h"

+ 10 - 0
package/gdb-microblaze/patches/patch-bfd_libbfd_h

@@ -0,0 +1,10 @@
+--- gdb-7.8.2.orig/bfd/libbfd.h	2015-01-15 11:58:11.000000000 +0100
++++ gdb-7.8.2/bfd/libbfd.h	2016-09-21 10:34:30.025222164 +0200
+@@ -2644,6 +2644,7 @@ static const char *const bfd_reloc_code_
+   "BFD_RELOC_MICROBLAZE_32_ROSDA",
+   "BFD_RELOC_MICROBLAZE_32_RWSDA",
+   "BFD_RELOC_MICROBLAZE_32_SYM_OP_SYM",
++  "BFD_RELOC_MICROBLAZE_32_NONE",
+   "BFD_RELOC_MICROBLAZE_64_NONE",
+   "BFD_RELOC_MICROBLAZE_64_GOTPC",
+   "BFD_RELOC_MICROBLAZE_64_GOT",

+ 20 - 0
package/gdb-microblaze/patches/patch-gdb_Makefile_in

@@ -0,0 +1,20 @@
+--- gdb-7.8.2.orig/gdb/Makefile.in	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/Makefile.in	2016-09-21 10:34:30.029222319 +0200
+@@ -912,7 +912,7 @@ top.h bsd-kvm.h gdb-stabs.h reggroups.h
+ annotate.h sim-regno.h dictionary.h dfp.h main.h frame-unwind.h	\
+ remote-fileio.h i386-linux-tdep.h vax-tdep.h objc-lang.h \
+ sentinel-frame.h bcache.h symfile.h windows-tdep.h linux-tdep.h \
+-gdb_usleep.h jit.h xml-syscall.h microblaze-tdep.h \
++gdb_usleep.h jit.h xml-syscall.h microblaze-tdep.h microblaze-linux-tdep.h \
+ psymtab.h psympriv.h progspace.h bfin-tdep.h ia64-hpux-tdep.h \
+ amd64-darwin-tdep.h charset-list.h \
+ config/djgpp/langinfo.h config/djgpp/nl_types.h darwin-nat.h \
+@@ -1639,7 +1639,7 @@ ALLDEPFILES = \
+ 	m68kbsd-nat.c m68kbsd-tdep.c \
+ 	m68klinux-nat.c m68klinux-tdep.c \
+ 	m88k-tdep.c m88kbsd-nat.c \
+-	microblaze-tdep.c microblaze-linux-tdep.c \
++	microblaze-tdep.c microblaze-linux-nat.c microblaze-linux-tdep.c \
+ 	mingw-hdep.c \
+ 	mips-linux-nat.c mips-linux-tdep.c \
+ 	mips-irix-tdep.c \

+ 3 - 3
package/gdb-microblaze/patches/patch-gdb_common_linux-ptrace_h

@@ -1,7 +1,7 @@
 * added from https://github.com/rofl0r/sabotage
 
---- gdb-7.6.orig/gdb/common/linux-ptrace.h	2013-01-01 07:32:54.000000000 +0100
-+++ gdb-7.6/gdb/common/linux-ptrace.h	2013-08-13 17:10:13.000000000 +0200
+--- gdb-7.8.2.orig/gdb/common/linux-ptrace.h	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/common/linux-ptrace.h	2016-09-21 10:34:30.005221389 +0200
 @@ -20,6 +20,7 @@
  
  struct buffer;
@@ -9,4 +9,4 @@
 +#include <unistd.h>
  #include <sys/ptrace.h>
  
- #ifndef PTRACE_GETSIGINFO
+ #ifdef __UCLIBC__

+ 3 - 3
package/gdb-microblaze/patches/patch-gdb_common_signals_c

@@ -1,8 +1,8 @@
 * added from https://github.com/rofl0r/sabotage
 
---- gdb-7.5.orig/gdb/common/signals.c	2012-05-24 18:51:37.000000000 +0200
-+++ gdb-7.5/gdb/common/signals.c	2012-10-01 14:44:23.000000000 +0200
-@@ -346,6 +346,8 @@ gdb_signal_from_host (int hostsig)
+--- gdb-7.8.2.orig/gdb/common/signals.c	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/common/signals.c	2016-09-21 10:34:30.009221544 +0200
+@@ -350,6 +350,8 @@ gdb_signal_from_host (int hostsig)
        else if (64 <= hostsig && hostsig <= 127)
  	return (enum gdb_signal)
  	  (hostsig - 64 + (int) GDB_SIGNAL_REALTIME_64);

+ 13 - 0
package/gdb-microblaze/patches/patch-gdb_config_microblaze_linux_mh

@@ -0,0 +1,13 @@
+--- gdb-7.8.2.orig/gdb/config/microblaze/linux.mh	1970-01-01 00:00:00.000000000 +0100
++++ gdb-7.8.2/gdb/config/microblaze/linux.mh	2016-09-21 10:34:30.025222164 +0200
+@@ -0,0 +1,10 @@
++# Host: Microblaze, running Linux
++
++NAT_FILE= config/nm-linux.h
++NATDEPFILES= inf-ptrace.o fork-child.o \
++	microblaze-linux-nat.o proc-service.o linux-thread-db.o \
++	linux-nat.o linux-osdata.o linux-fork.o linux-procfs.o linux-ptrace.o \
++	linux-waitpid.o
++NAT_CDEPS = $(srcdir)/proc-service.list
++
++LOADLIBES = -ldl $(RDYNAMIC)

+ 19 - 0
package/gdb-microblaze/patches/patch-gdb_configure_host

@@ -0,0 +1,19 @@
+--- gdb-7.8.2.orig/gdb/configure.host	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/configure.host	2016-09-21 10:34:30.025222164 +0200
+@@ -59,6 +59,7 @@ i[34567]86*)		gdb_host_cpu=i386 ;;
+ m68*)			gdb_host_cpu=m68k ;;
+ m88*)			gdb_host_cpu=m88k ;;
+ mips*)			gdb_host_cpu=mips ;;
++microblaze*)		gdb_host_cpu=microblaze ;;
+ powerpc* | rs6000)	gdb_host_cpu=powerpc ;;
+ sparcv9 | sparc64)	gdb_host_cpu=sparc ;;
+ s390*)			gdb_host_cpu=s390 ;;
+@@ -133,6 +134,8 @@ mips*-*-netbsd* | mips*-*-knetbsd*-gnu)
+ 			gdb_host=nbsd ;;
+ mips64*-*-openbsd*)	gdb_host=obsd64 ;;
+ 
++microblaze*-*linux*)    gdb_host=linux ;;
++
+ powerpc-*-aix* | rs6000-*-* | powerpc64-*-aix*)
+ 			gdb_host=aix ;;
+ powerpc*-*-freebsd*)	gdb_host=fbsd ;;

+ 14 - 0
package/gdb-microblaze/patches/patch-gdb_configure_tgt

@@ -0,0 +1,14 @@
+--- gdb-7.8.2.orig/gdb/configure.tgt	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/configure.tgt	2016-09-21 10:34:30.025222164 +0200
+@@ -340,9 +340,10 @@ mep-*-*)
+ 
+ microblaze*-linux-*|microblaze*-*-linux*)
+ 	# Target: Xilinx MicroBlaze running Linux
+-	gdb_target_obs="microblaze-tdep.o microblaze-linux-tdep.o microblaze-rom.o \
++	gdb_target_obs="microblaze-tdep.o microblaze-linux-tdep.o microblaze-rom.o glibc-tdep.o \
+ 			monitor.o dsrec.o solib-svr4.o symfile-mem.o linux-tdep.o"
+ 	gdb_sim=../sim/microblaze/libsim.a
++	build_gdbserver=yes
+ 	;;
+ microblaze*-*-*)
+ 	# Target: Xilinx MicroBlaze running standalone

+ 51 - 0
package/gdb-microblaze/patches/patch-gdb_debugreg_h

@@ -0,0 +1,51 @@
+--- gdb-7.8.2.orig/gdb/debugreg.h	1970-01-01 00:00:00.000000000 +0100
++++ gdb-7.8.2/gdb/debugreg.h	2016-09-20 19:56:32.003878822 +0200
+@@ -0,0 +1,48 @@
++#ifndef SYS_DEBUGREG_H
++#define SYS_DEBUGREG_H
++
++#include <stdint.h>
++
++#define DR_FIRSTADDR 0
++#define DR_LASTADDR 3
++
++#define DR_STATUS 6
++#define DR_CONTROL 7
++
++#define DR_TRAP0        (0x1)
++#define DR_TRAP1        (0x2)
++#define DR_TRAP2        (0x4)
++#define DR_TRAP3        (0x8)
++
++#define DR_STEP         (0x4000)
++#define DR_SWITCH       (0x8000)
++
++#define DR_CONTROL_SHIFT 16
++#define DR_CONTROL_SIZE  4
++
++#define DR_RW_EXECUTE   (0x0)
++#define DR_RW_WRITE     (0x1)
++#define DR_RW_READ      (0x3)
++
++#define DR_LEN_1 (0x0)
++#define DR_LEN_2 (0x4)
++#define DR_LEN_4 (0xC)
++#define DR_LEN_8 (0x8)
++
++#define DR_LOCAL_ENABLE_SHIFT  0
++#define DR_GLOBAL_ENABLE_SHIFT 1
++#define DR_ENABLE_SIZE         2
++
++#define DR_LOCAL_ENABLE_MASK  (0x55)
++#define DR_GLOBAL_ENABLE_MASK (0xAA)
++
++
++#if SIZE_MAX > 4294967295
++# define DR_CONTROL_RESERVED (0xFFFFFFFF0000FC00UL)
++#else
++# define DR_CONTROL_RESERVED (0x00FC00U)
++#endif
++#define DR_LOCAL_SLOWDOWN   (0x100)
++#define DR_GLOBAL_SLOWDOWN  (0x200)
++
++#endif

+ 27 - 0
package/gdb-microblaze/patches/patch-gdb_gdbserver_Makefile_in

@@ -0,0 +1,27 @@
+--- gdb-7.8.2.orig/gdb/gdbserver/Makefile.in	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/gdbserver/Makefile.in	2016-09-21 10:34:30.025222164 +0200
+@@ -148,6 +148,7 @@ SFILES=	$(srcdir)/gdbreplay.c $(srcdir)/
+ 	$(srcdir)/linux-ia64-low.c $(srcdir)/linux-low.c \
+ 	$(srcdir)/linux-m32r-low.c \
+ 	$(srcdir)/linux-m68k-low.c $(srcdir)/linux-mips-low.c \
++	$(srcdir)/linux-microblaze-low.c \
+ 	$(srcdir)/linux-nios2-low.c \
+ 	$(srcdir)/linux-ppc-low.c \
+ 	$(srcdir)/linux-s390-low.c \
+@@ -329,6 +330,7 @@ clean:
+ 	rm -f arm-with-iwmmxt.c
+ 	rm -f arm-with-vfpv2.c arm-with-vfpv3.c arm-with-neon.c
+ 	rm -f mips-linux.c mips64-linux.c
++	rm -f microblaze-linux.c
+ 	rm -f nios2-linux.c
+ 	rm -f powerpc-32.c powerpc-32l.c powerpc-64l.c powerpc-e500l.c
+ 	rm -f powerpc-altivec32l.c powerpc-cell32l.c powerpc-vsx32l.c
+@@ -620,6 +622,8 @@ mips64-linux.c : $(srcdir)/../regformats
+ 	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/mips64-linux.dat mips64-linux.c
+ mips64-dsp-linux.c : $(srcdir)/../regformats/mips64-dsp-linux.dat $(regdat_sh)
+ 	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/mips64-dsp-linux.dat mips64-dsp-linux.c
++microblaze-linux.c : $(srcdir)/../regformats/reg-microblaze.dat $(regdat_sh)
++	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/reg-microblaze.dat microblaze-linux.c
+ nios2-linux.c :	$(srcdir)/../regformats/nios2-linux.dat $(regdat_sh)
+ 	$(SHELL) $(regdat_sh) $(srcdir)/../regformats/nios2-linux.dat nios2-linux.c
+ powerpc-32.c : $(srcdir)/../regformats/rs6000/powerpc-32.dat $(regdat_sh)

+ 4 - 4
package/gdb-microblaze/patches/patch-gdb_gdbserver_configure

@@ -1,6 +1,6 @@
---- gdb-7.6.orig/gdb/gdbserver/configure	2013-03-11 09:35:09.000000000 +0100
-+++ gdb-7.6/gdb/gdbserver/configure	2013-12-23 19:39:06.000000000 +0100
-@@ -4927,9 +4927,6 @@ if test "${GCC}" = yes -a -z "${ERROR_ON
+--- gdb-7.8.2.orig/gdb/gdbserver/configure	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/gdbserver/configure	2016-09-21 10:34:30.013221699 +0200
+@@ -5250,9 +5250,6 @@ if test "${GCC}" = yes -a -z "${ERROR_ON
  fi
  
  WERROR_CFLAGS=""
@@ -10,7 +10,7 @@
  
  build_warnings="-Wall -Wdeclaration-after-statement -Wpointer-arith \
  -Wformat-nonliteral -Wno-char-subscripts -Wempty-body"
-@@ -4943,7 +4940,6 @@ $as_echo_n "checking compiler warning fl
+@@ -5266,7 +5263,6 @@ $as_echo_n "checking compiler warning fl
      # compiled with it enabled.
      for w in ${build_warnings}; do
  	case $w in

+ 16 - 0
package/gdb-microblaze/patches/patch-gdb_gdbserver_configure_srv

@@ -0,0 +1,16 @@
+--- gdb-7.8.2.orig/gdb/gdbserver/configure.srv	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/gdbserver/configure.srv	2016-09-21 10:34:30.025222164 +0200
+@@ -198,6 +198,13 @@ case "${target}" in
+ 			srv_linux_usrregs=yes
+ 			srv_linux_thread_db=yes
+ 			;;
++  microblaze*-*-linux*)	srv_regobj=microblaze-linux.o
++			srv_tgtobj="$srv_linux_obj linux-microblaze-low.o"
++			srv_linux_usrregs=yes
++			srv_linux_regsets=yes
++			srv_linux_thread_db=yes
++			;;
++
+   nios2*-*-linux*)	srv_regobj="nios2-linux.o"
+ 			srv_tgtobj="$srv_linux_obj linux-nios2-low.o"
+ 			srv_xmlfiles="nios2-linux.xml"

+ 232 - 0
package/gdb-microblaze/patches/patch-gdb_gdbserver_linux-microblaze-low_c

@@ -0,0 +1,232 @@
+--- gdb-7.8.2.orig/gdb/gdbserver/linux-microblaze-low.c	1970-01-01 00:00:00.000000000 +0100
++++ gdb-7.8.2/gdb/gdbserver/linux-microblaze-low.c	2016-09-21 10:34:30.025222164 +0200
+@@ -0,0 +1,228 @@
++/* GNU/Linux/Microblaze specific low level interface, for the remote server for
++   GDB.
++   Copyright (C) 1995-2013 Free Software Foundation, Inc.
++
++   This file is part of GDB.
++
++   This program is free software; you can redistribute it and/or modify
++   it under the terms of the GNU General Public License as published by
++   the Free Software Foundation; either version 3 of the License, or
++   (at your option) any later version.
++
++   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, see <http://www.gnu.org/licenses/>.  */
++
++#include "server.h"
++#include "linux-low.h"
++
++#include <asm/ptrace.h>
++#include <sys/procfs.h>
++#include <sys/ptrace.h>
++
++#include "gdb_proc_service.h"
++
++static int microblaze_regmap[] =
++ {PT_GPR(0),     PT_GPR(1),     PT_GPR(2),     PT_GPR(3),
++  PT_GPR(4),     PT_GPR(5),     PT_GPR(6),     PT_GPR(7),
++  PT_GPR(8),     PT_GPR(9),     PT_GPR(10),    PT_GPR(11),
++  PT_GPR(12),    PT_GPR(13),    PT_GPR(14),    PT_GPR(15),
++  PT_GPR(16),    PT_GPR(17),    PT_GPR(18),    PT_GPR(19),
++  PT_GPR(20),    PT_GPR(21),    PT_GPR(22),    PT_GPR(23),
++  PT_GPR(24),    PT_GPR(25),    PT_GPR(26),    PT_GPR(27),
++  PT_GPR(28),    PT_GPR(29),    PT_GPR(30),    PT_GPR(31),
++  PT_PC,         PT_MSR,        PT_EAR,        PT_ESR,
++  PT_FSR
++  };
++
++#define microblaze_num_regs (sizeof microblaze_regmap / sizeof microblaze_regmap[0])
++
++/* Defined in auto-generated file microblaze-linux.c.  */
++void init_registers_microblaze (void);
++extern const struct target_desc *tdesc_microblaze;
++
++static int
++microblaze_cannot_store_register (int regno)
++{
++  if (microblaze_regmap[regno] == -1 || regno == 0)
++    return 1;
++
++  return 0;
++}
++
++static int
++microblaze_cannot_fetch_register (int regno)
++{
++  return 0;
++}
++
++static CORE_ADDR
++microblaze_get_pc (struct regcache *regcache)
++{
++  unsigned long pc;
++
++  collect_register_by_name (regcache, "pc", &pc);
++  return (CORE_ADDR) pc;
++}
++
++static void
++microblaze_set_pc (struct regcache *regcache, CORE_ADDR pc)
++{
++  unsigned long newpc = pc;
++
++  supply_register_by_name (regcache, "pc", &newpc);
++}
++
++/* dbtrap insn */
++/* brki r16, 0x18; */
++static const unsigned long microblaze_breakpoint = 0xba0c0018;
++#define microblaze_breakpoint_len 4
++
++static int
++microblaze_breakpoint_at (CORE_ADDR where)
++{
++  unsigned long insn;
++
++  (*the_target->read_memory) (where, (unsigned char *) &insn, 4);
++  if (insn == microblaze_breakpoint)
++    return 1;
++  /* If necessary, recognize more trap instructions here.  GDB only uses the
++     one.  */
++  return 0;
++}
++
++static CORE_ADDR
++microblaze_reinsert_addr (struct regcache *regcache)
++{
++  unsigned long pc;
++  collect_register_by_name (regcache, "r15", &pc);
++  return pc;
++}
++
++#ifdef HAVE_PTRACE_GETREGS
++
++static void
++microblaze_collect_ptrace_register (struct regcache *regcache, int regno, char *buf)
++{
++  int size = register_size (regcache->tdesc, regno);
++
++  memset (buf, 0, sizeof (long));
++
++  if (size < sizeof (long))
++    collect_register (regcache, regno, buf + sizeof (long) - size);
++  else
++    collect_register (regcache, regno, buf);
++}
++
++static void
++microblaze_supply_ptrace_register (struct regcache *regcache,
++			    int regno, const char *buf)
++{
++  int size = register_size (regcache->tdesc, regno);
++
++  if (regno == 0) {
++    unsigned long regbuf_0 = 0;
++    /* clobbering r0 so that it is always 0 as enforced by hardware */
++    supply_register (regcache, regno, (const char*)&regbuf_0);
++  } else {
++      if (size < sizeof (long))
++        supply_register (regcache, regno, buf + sizeof (long) - size);
++      else
++        supply_register (regcache, regno, buf);
++  }
++}
++
++/* Provide only a fill function for the general register set.  ps_lgetregs
++   will use this for NPTL support.  */
++
++static void microblaze_fill_gregset (struct regcache *regcache, void *buf)
++{
++  int i;
++
++  for (i = 0; i < 32; i++)
++    microblaze_collect_ptrace_register (regcache, i, (char *) buf + microblaze_regmap[i]);
++}
++
++static void
++microblaze_store_gregset (struct regcache *regcache, const void *buf)
++{
++  int i;
++
++  for (i = 0; i < 32; i++)
++    supply_register (regcache, i, (char *) buf + microblaze_regmap[i]);
++}
++
++#endif /* HAVE_PTRACE_GETREGS */
++
++static struct regset_info microblaze_regsets[] = {
++#ifdef HAVE_PTRACE_GETREGS
++  { PTRACE_GETREGS, PTRACE_SETREGS, 0, sizeof (elf_gregset_t), GENERAL_REGS, microblaze_fill_gregset, microblaze_store_gregset },
++  { 0, 0, 0, -1, -1, NULL, NULL },
++#endif /* HAVE_PTRACE_GETREGS */
++  { 0, 0, 0, -1, -1, NULL, NULL }
++};
++
++static struct regsets_info microblaze_regsets_info =
++  {
++    microblaze_regsets, /* regsets */
++    0, /* num_regsets */
++    NULL, /* disabled_regsets */
++  };
++
++static struct usrregs_info microblaze_usrregs_info =
++  {
++    microblaze_num_regs,
++    microblaze_regmap,
++  };
++
++static struct regs_info regs_info =
++  {
++    NULL, /* regset_bitmap */
++    &microblaze_usrregs_info,
++    &microblaze_regsets_info
++  };
++
++static const struct regs_info *
++microblaze_regs_info (void)
++{
++  return &regs_info;
++}
++
++static void
++microblaze_arch_setup (void)
++{
++  current_process ()->tdesc = tdesc_microblaze;
++}
++
++struct linux_target_ops the_low_target = {
++  microblaze_arch_setup,
++  microblaze_regs_info,
++  microblaze_cannot_fetch_register,
++  microblaze_cannot_store_register,
++  NULL, /* fetch_register */
++  microblaze_get_pc,
++  microblaze_set_pc,
++  (const unsigned char *) &microblaze_breakpoint,
++  microblaze_breakpoint_len,
++  microblaze_reinsert_addr,
++  0,
++  microblaze_breakpoint_at,
++  NULL,
++  NULL,
++  NULL,
++  NULL,
++  microblaze_collect_ptrace_register,
++  microblaze_supply_ptrace_register,
++};
++
++void
++initialize_low_arch (void)
++{
++  init_registers_microblaze ();
++
++  initialize_regsets_info (&microblaze_regsets_info);
++}
+\ No newline at end of file

+ 4 - 4
package/gdb-microblaze/patches/patch-gdb_linux-nat_c

@@ -1,8 +1,8 @@
 * added from https://github.com/rofl0r/sabotage
 
---- gdb-7.6.orig/gdb/linux-nat.c	2013-02-13 15:59:49.000000000 +0100
-+++ gdb-7.6/gdb/linux-nat.c	2013-08-13 17:01:09.000000000 +0200
-@@ -79,6 +79,14 @@
+--- gdb-7.8.2.orig/gdb/linux-nat.c	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/linux-nat.c	2016-09-21 10:34:30.017221854 +0200
+@@ -81,6 +81,14 @@
  # endif
  #endif /* HAVE_PERSONALITY */
  
@@ -17,7 +17,7 @@
  /* This comment documents high-level logic of this file.
  
  Waiting for events in sync mode
-@@ -2379,7 +2387,7 @@ linux_handle_extended_wait (struct lwp_i
+@@ -2118,7 +2126,7 @@ linux_handle_extended_wait (struct lwp_i
  		status = 0;
  	    }
  

+ 433 - 0
package/gdb-microblaze/patches/patch-gdb_microblaze-linux-nat_c

@@ -0,0 +1,433 @@
+--- gdb-7.8.2.orig/gdb/microblaze-linux-nat.c	1970-01-01 00:00:00.000000000 +0100
++++ gdb-7.8.2/gdb/microblaze-linux-nat.c	2016-09-21 10:34:30.029222319 +0200
+@@ -0,0 +1,430 @@
++/* Microblaze GNU/Linux native support.
++
++   Copyright (C) 1988-1989, 1991-1992, 1994, 1996, 2000-2012 Free
++   Software Foundation, Inc.
++
++   This file is part of GDB.
++
++   This program is free software; you can redistribute it and/or modify
++   it under the terms of the GNU General Public License as published by
++   the Free Software Foundation; either version 3 of the License, or
++   (at your option) any later version.
++
++   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, see <http://www.gnu.org/licenses/>.  */
++
++#include "defs.h"
++#include "arch-utils.h"
++#include "dis-asm.h"
++#include "frame.h"
++#include "trad-frame.h"
++#include "symtab.h"
++#include "value.h"
++#include "gdbcmd.h"
++#include "breakpoint.h"
++#include "inferior.h"
++#include "regcache.h"
++#include "target.h"
++#include "frame.h"
++#include "frame-base.h"
++#include "frame-unwind.h"
++#include "dwarf2-frame.h"
++#include "osabi.h"
++
++#include "gdb_assert.h"
++#include "target-descriptions.h"
++#include "opcodes/microblaze-opcm.h"
++#include "opcodes/microblaze-dis.h"
++
++#include "linux-nat.h"
++#include "target-descriptions.h"
++
++#include <sys/user.h>
++#include <sys/utsname.h>
++#include <sys/procfs.h>
++#include <sys/ptrace.h>
++
++/* Prototypes for supply_gregset etc. */
++#include "gregset.h"
++
++#include "microblaze-tdep.h"
++
++#include <elf/common.h>
++#include "auxv.h"
++
++/* Defines ps_err_e, struct ps_prochandle.  */
++#include "gdb_proc_service.h"
++
++/* On GNU/Linux, threads are implemented as pseudo-processes, in which
++   case we may be tracing more than one process at a time.  In that
++   case, inferior_ptid will contain the main process ID and the
++   individual thread (process) ID.  get_thread_id () is used to get
++   the thread id if it's available, and the process id otherwise.  */
++
++int
++get_thread_id (ptid_t ptid)
++{
++  int tid = ptid_get_lwp (ptid);
++  if (0 == tid)
++    tid = ptid_get_pid (ptid);
++  return tid;
++}
++
++#define GET_THREAD_ID(PTID)	get_thread_id (PTID)
++
++/* Non-zero if our kernel may support the PTRACE_GETREGS and
++   PTRACE_SETREGS requests, for reading and writing the
++   general-purpose registers.  Zero if we've tried one of
++   them and gotten an error.  */
++int have_ptrace_getsetregs = 1;
++
++static int
++microblaze_register_u_addr (struct gdbarch *gdbarch, int regno)
++{
++  int u_addr = -1;
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  /* NOTE: cagney/2003-11-25: This is the word size used by the ptrace
++     interface, and not the wordsize of the program's ABI.  */
++  int wordsize = sizeof (long);
++
++  /* General purpose registers occupy 1 slot each in the buffer.  */
++  if (regno >= MICROBLAZE_R0_REGNUM
++      && regno <= MICROBLAZE_FSR_REGNUM)
++    u_addr = (regno * wordsize);
++
++  return u_addr;
++}
++
++
++static void
++fetch_register (struct regcache *regcache, int tid, int regno)
++{
++  struct gdbarch *gdbarch = get_regcache_arch (regcache);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  /* This isn't really an address.  But ptrace thinks of it as one.  */
++  CORE_ADDR regaddr = microblaze_register_u_addr (gdbarch, regno);
++  int bytes_transferred;
++  unsigned int offset;         /* Offset of registers within the u area.  */
++  char buf[MAX_REGISTER_SIZE];
++
++  if (regaddr == -1)
++  {
++    memset (buf, '\0', register_size (gdbarch, regno));   /* Supply zeroes */
++    regcache_raw_supply (regcache, regno, buf);
++    return;
++  }
++
++  /* Read the raw register using sizeof(long) sized chunks.  On a
++     32-bit platform, 64-bit floating-point registers will require two
++     transfers.  */
++  for (bytes_transferred = 0;
++       bytes_transferred < register_size (gdbarch, regno);
++       bytes_transferred += sizeof (long))
++  {
++    long l;
++
++    errno = 0;
++    l = ptrace (PTRACE_PEEKUSER, tid, (PTRACE_TYPE_ARG3) regaddr, 0);
++    regaddr += sizeof (long);
++    if (errno != 0)
++    {
++      char message[128];
++      sprintf (message, "reading register %s (#%d)",
++               gdbarch_register_name (gdbarch, regno), regno);
++      perror_with_name (message);
++    }
++    memcpy (&buf[bytes_transferred], &l, sizeof (l));
++  }
++
++  /* Now supply the register.  Keep in mind that the regcache's idea
++     of the register's size may not be a multiple of sizeof
++     (long).  */
++  if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_LITTLE)
++  {
++    /* Little-endian values are always found at the left end of the
++       bytes transferred.  */
++    regcache_raw_supply (regcache, regno, buf);
++  }
++  else if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
++  {
++    /* Big-endian values are found at the right end of the bytes
++       transferred.  */
++    size_t padding = (bytes_transferred - register_size (gdbarch, regno));
++    regcache_raw_supply (regcache, regno, buf + padding);
++  }
++  else
++    internal_error (__FILE__, __LINE__,
++                    _("fetch_register: unexpected byte order: %d"),
++                    gdbarch_byte_order (gdbarch));
++}
++
++/* This function actually issues the request to ptrace, telling
++   it to get all general-purpose registers and put them into the
++   specified regset.
++
++   If the ptrace request does not exist, this function returns 0
++   and properly sets the have_ptrace_* flag.  If the request fails,
++   this function calls perror_with_name.  Otherwise, if the request
++   succeeds, then the regcache gets filled and 1 is returned.  */
++static int
++fetch_all_gp_regs (struct regcache *regcache, int tid)
++{
++  struct gdbarch *gdbarch = get_regcache_arch (regcache);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  gdb_gregset_t gregset;
++
++  if (ptrace (PTRACE_GETREGS, tid, 0, (void *) &gregset) < 0)
++  {
++    if (errno == EIO)
++    {
++      have_ptrace_getsetregs = 0;
++      return 0;
++    }
++    perror_with_name (_("Couldn't get general-purpose registers."));
++  }
++
++  supply_gregset (regcache, (const gdb_gregset_t *) &gregset);
++
++  return 1;
++}
++
++
++/* This is a wrapper for the fetch_all_gp_regs function.  It is
++   responsible for verifying if this target has the ptrace request
++   that can be used to fetch all general-purpose registers at one
++   shot.  If it doesn't, then we should fetch them using the
++   old-fashioned way, which is to iterate over the registers and
++   request them one by one.  */
++static void
++fetch_gp_regs (struct regcache *regcache, int tid)
++{
++  struct gdbarch *gdbarch = get_regcache_arch (regcache);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  int i;
++
++  if (have_ptrace_getsetregs)
++    if (fetch_all_gp_regs (regcache, tid))
++      return;
++
++  /* If we've hit this point, it doesn't really matter which
++     architecture we are using.  We just need to read the
++     registers in the "old-fashioned way".  */
++  for (i = MICROBLAZE_R0_REGNUM; i <= MICROBLAZE_FSR_REGNUM; i++)
++    fetch_register (regcache, tid, i);
++}
++
++
++static void
++store_register (const struct regcache *regcache, int tid, int regno)
++{
++  struct gdbarch *gdbarch = get_regcache_arch (regcache);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  /* This isn't really an address.  But ptrace thinks of it as one.  */
++  CORE_ADDR regaddr = microblaze_register_u_addr (gdbarch, regno);
++  int i;
++  size_t bytes_to_transfer;
++  char buf[MAX_REGISTER_SIZE];
++
++  if (regaddr == -1)
++    return;
++
++  /* First collect the register.  Keep in mind that the regcache's
++     idea of the register's size may not be a multiple of sizeof
++     (long).  */
++  memset (buf, 0, sizeof buf);
++  bytes_to_transfer = align_up (register_size (gdbarch, regno), sizeof (long));
++  if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_LITTLE)
++  {
++    /* Little-endian values always sit at the left end of the buffer.  */
++    regcache_raw_collect (regcache, regno, buf);
++  }
++  else if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
++  {
++    /* Big-endian values sit at the right end of the buffer.  */
++    size_t padding = (bytes_to_transfer - register_size (gdbarch, regno));
++    regcache_raw_collect (regcache, regno, buf + padding);
++  }
++
++  for (i = 0; i < bytes_to_transfer; i += sizeof (long))
++  {
++    long l;
++
++    memcpy (&l, &buf[i], sizeof (l));
++    errno = 0;
++    ptrace (PTRACE_POKEUSER, tid, (PTRACE_TYPE_ARG3) regaddr, l);
++    regaddr += sizeof (long);
++
++    if (errno != 0)
++    {
++      char message[128];
++      sprintf (message, "writing register %s (#%d)",
++               gdbarch_register_name (gdbarch, regno), regno);
++      perror_with_name (message);
++    }
++  }
++}
++
++/* This function actually issues the request to ptrace, telling
++   it to store all general-purpose registers present in the specified
++   regset.
++
++   If the ptrace request does not exist, this function returns 0
++   and properly sets the have_ptrace_* flag.  If the request fails,
++   this function calls perror_with_name.  Otherwise, if the request
++   succeeds, then the regcache is stored and 1 is returned.  */
++static int
++store_all_gp_regs (const struct regcache *regcache, int tid, int regno)
++{
++  struct gdbarch *gdbarch = get_regcache_arch (regcache);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  gdb_gregset_t gregset;
++
++  if (ptrace (PTRACE_GETREGS, tid, 0, (void *) &gregset) < 0)
++    {
++      if (errno == EIO)
++      {
++        have_ptrace_getsetregs = 0;
++        return 0;
++      }
++      perror_with_name (_("Couldn't get general-purpose registers."));
++    }
++
++  fill_gregset (regcache, &gregset, regno);
++
++  if (ptrace (PTRACE_SETREGS, tid, 0, (void *) &gregset) < 0)
++    {
++      if (errno == EIO)
++      {
++        have_ptrace_getsetregs = 0;
++        return 0;
++      }
++      perror_with_name (_("Couldn't set general-purpose registers."));
++    }
++
++  return 1;
++}
++
++/* This is a wrapper for the store_all_gp_regs function.  It is
++   responsible for verifying if this target has the ptrace request
++   that can be used to store all general-purpose registers at one
++   shot.  If it doesn't, then we should store them using the
++   old-fashioned way, which is to iterate over the registers and
++   store them one by one.  */
++static void
++store_gp_regs (const struct regcache *regcache, int tid, int regno)
++{
++  struct gdbarch *gdbarch = get_regcache_arch (regcache);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++  int i;
++
++  if (have_ptrace_getsetregs)
++    if (store_all_gp_regs (regcache, tid, regno))
++      return;
++
++  /* If we hit this point, it doesn't really matter which
++     architecture we are using.  We just need to store the
++     registers in the "old-fashioned way".  */
++  for (i = MICROBLAZE_R0_REGNUM; i <= MICROBLAZE_FSR_REGNUM; i++)
++    store_register (regcache, tid, i);
++}
++
++
++/* Fetch registers from the child process.  Fetch all registers if
++   regno == -1, otherwise fetch all general registers or all floating
++   point registers depending upon the value of regno.  */
++
++static void
++microblaze_linux_fetch_inferior_registers (struct target_ops *ops,
++				    struct regcache *regcache, int regno)
++{
++  /* Get the thread id for the ptrace call.  */
++  int tid = GET_THREAD_ID (inferior_ptid);
++
++  if (regno == -1)
++    fetch_gp_regs (regcache, tid);
++  else
++    fetch_register (regcache, tid, regno);
++}
++
++/* Store registers back into the inferior.  Store all registers if
++   regno == -1, otherwise store all general registers or all floating
++   point registers depending upon the value of regno.  */
++
++static void
++microblaze_linux_store_inferior_registers (struct target_ops *ops,
++				    struct regcache *regcache, int regno)
++{
++  /* Get the thread id for the ptrace call.  */
++  int tid = GET_THREAD_ID (inferior_ptid);
++
++  if (regno >= 0)
++    store_register (regcache, tid, regno);
++  else
++    store_gp_regs (regcache, tid, -1);
++}
++
++/* Wrapper functions for the standard regset handling, used by
++   thread debugging.  */
++
++void
++fill_gregset (const struct regcache *regcache,
++	      gdb_gregset_t *gregsetp, int regno)
++{
++  microblaze_collect_gregset (NULL, regcache, regno, gregsetp);
++}
++
++void
++supply_gregset (struct regcache *regcache, const gdb_gregset_t *gregsetp)
++{
++  microblaze_supply_gregset (NULL, regcache, -1, gregsetp);
++}
++
++void
++fill_fpregset (const struct regcache *regcache,
++	      gdb_fpregset_t *fpregsetp, int regno)
++{
++  /* FIXME. */
++}
++
++void
++supply_fpregset (struct regcache *regcache, const gdb_fpregset_t *fpregsetp)
++{
++  /* FIXME. */
++}
++
++static const struct target_desc *
++microblaze_linux_read_description (struct target_ops *ops)
++{
++  CORE_ADDR microblaze_hwcap = 0;
++
++  if (target_auxv_search (ops, AT_HWCAP, &microblaze_hwcap) != 1)
++    return NULL;
++
++  return NULL;
++}
++
++
++void _initialize_microblaze_linux_nat (void);
++
++void
++_initialize_microblaze_linux_nat (void)
++{
++  struct target_ops *t;
++
++  /* Fill in the generic GNU/Linux methods.  */
++  t = linux_target ();
++
++  /* Add our register access methods.  */
++  t->to_fetch_registers = microblaze_linux_fetch_inferior_registers;
++  t->to_store_registers = microblaze_linux_store_inferior_registers;
++
++  t->to_read_description = microblaze_linux_read_description;
++
++  /* Register the target.  */
++  linux_nat_add_target (t);
++}

+ 155 - 0
package/gdb-microblaze/patches/patch-gdb_microblaze-linux-tdep_c

@@ -0,0 +1,155 @@
+--- gdb-7.8.2.orig/gdb/microblaze-linux-tdep.c	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/microblaze-linux-tdep.c	2016-09-21 10:34:30.029222319 +0200
+@@ -1,6 +1,6 @@
+ /* Target-dependent code for Xilinx MicroBlaze.
+ 
+-   Copyright (C) 2009-2014 Free Software Foundation, Inc.
++   Copyright (C) 2009-2013 Free Software Foundation, Inc.
+ 
+    This file is part of GDB.
+ 
+@@ -32,11 +32,28 @@
+ #include "regset.h"
+ #include "solib-svr4.h"
+ #include "microblaze-tdep.h"
++#include "glibc-tdep.h"
+ #include "trad-frame.h"
+ #include "frame-unwind.h"
+ #include "tramp-frame.h"
+ #include "linux-tdep.h"
+ 
++static int microblaze_debug_flag = 0;
++
++static void
++microblaze_debug (const char *fmt, ...)
++{
++  if (microblaze_debug_flag)
++    {
++       va_list args;
++
++       va_start (args, fmt);
++       printf_unfiltered ("MICROBLAZE LINUX: ");
++       vprintf_unfiltered (fmt, args);
++       va_end (args);
++    }
++}
++
+ static int
+ microblaze_linux_memory_remove_breakpoint (struct gdbarch *gdbarch, 
+ 					   struct bp_target_info *bp_tgt)
+@@ -46,20 +63,27 @@ microblaze_linux_memory_remove_breakpoin
+   int val;
+   int bplen;
+   gdb_byte old_contents[BREAKPOINT_MAX];
++  struct cleanup *cleanup;
+ 
+   /* Determine appropriate breakpoint contents and size for this address.  */
+   bp = gdbarch_breakpoint_from_pc (gdbarch, &addr, &bplen);
+   if (bp == NULL)
+     error (_("Software breakpoints not implemented for this target."));
+ 
++  /* Make sure we see the memory breakpoints.  */
++  cleanup = make_show_memory_breakpoints_cleanup (1);
+   val = target_read_memory (addr, old_contents, bplen);
+ 
+   /* If our breakpoint is no longer at the address, this means that the
+      program modified the code on us, so it is wrong to put back the
+      old value.  */
+   if (val == 0 && memcmp (bp, old_contents, bplen) == 0)
+-    val = target_write_raw_memory (addr, bp_tgt->shadow_contents, bplen);
++  {
++      val = target_write_raw_memory (addr, bp_tgt->shadow_contents, bplen);
++      microblaze_debug ("microblaze_linux_memory_remove_breakpoint writing back to memory at addr 0x%lx\n", addr);
++  }
+ 
++  do_cleanups (cleanup);
+   return val;
+ }
+ 
+@@ -116,6 +140,50 @@ static struct tramp_frame microblaze_lin
+   microblaze_linux_sighandler_cache_init
+ };
+ 
++const struct microblaze_gregset microblaze_linux_core_gregset;
++
++static void
++microblaze_linux_supply_core_gregset (const struct regset *regset,
++                                   struct regcache *regcache,
++                                   int regnum, const void *gregs, size_t len)
++{
++  microblaze_supply_gregset (&microblaze_linux_core_gregset, regcache,
++                             regnum, gregs);
++}
++
++static void
++microblaze_linux_collect_core_gregset (const struct regset *regset,
++                                    const struct regcache *regcache,
++                                    int regnum, void *gregs, size_t len)
++{
++  microblaze_collect_gregset (&microblaze_linux_core_gregset, regcache,
++                              regnum, gregs);
++}
++
++static void
++microblaze_linux_supply_core_fpregset (const struct regset *regset,
++                                    struct regcache *regcache,
++                                    int regnum, const void *fpregs, size_t len)
++{
++  /* FIXME.  */
++  microblaze_supply_fpregset (regcache, regnum, fpregs);
++}
++
++static void
++microblaze_linux_collect_core_fpregset (const struct regset *regset,
++                                     const struct regcache *regcache,
++                                     int regnum, void *fpregs, size_t len)
++{
++  /* FIXME.  */
++  microblaze_collect_fpregset (regcache, regnum, fpregs);
++}
++
++static const struct regset microblaze_linux_gregset =
++{
++    NULL,
++    microblaze_linux_supply_core_gregset,
++    microblaze_linux_collect_core_gregset
++};
+ 
+ static void
+ microblaze_linux_init_abi (struct gdbarch_info info,
+@@ -123,6 +191,9 @@ microblaze_linux_init_abi (struct gdbarc
+ {
+   struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+ 
++  tdep->gregset = &microblaze_linux_gregset;
++  tdep->sizeof_gregset = 200;
++
+   linux_init_abi (info, gdbarch);
+ 
+   set_gdbarch_memory_remove_breakpoint (gdbarch,
+@@ -135,6 +206,25 @@ microblaze_linux_init_abi (struct gdbarc
+   /* Trampolines.  */
+   tramp_frame_prepend_unwinder (gdbarch,
+ 				&microblaze_linux_sighandler_tramp_frame);
++
++  /* BFD target for core files.  */
++  if (gdbarch_byte_order (gdbarch) == BFD_ENDIAN_BIG)
++    set_gdbarch_gcore_bfd_target (gdbarch, "elf32-microblaze");
++  else
++    set_gdbarch_gcore_bfd_target (gdbarch, "elf32-microblazeel");
++
++
++  /* Shared library handling.  */
++  set_gdbarch_skip_trampoline_code (gdbarch, find_solib_trampoline_target);
++  set_gdbarch_skip_solib_resolver (gdbarch, glibc_skip_solib_resolver);
++
++  set_gdbarch_regset_from_core_section (gdbarch,
++					microblaze_regset_from_core_section);
++
++  /* Enable TLS support.  */
++  set_gdbarch_fetch_tls_load_module_address (gdbarch,
++                                             svr4_fetch_objfile_link_map);
++
+ }
+ 
+ /* -Wmissing-prototypes */

+ 18 - 0
package/gdb-microblaze/patches/patch-gdb_microblaze-rom_c

@@ -0,0 +1,18 @@
+--- gdb-7.8.2.orig/gdb/microblaze-rom.c	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/microblaze-rom.c	2016-09-21 10:34:30.029222319 +0200
+@@ -1,6 +1,6 @@
+ /* Remote debugging interface to Xilinx MicroBlaze.
+ 
+-   Copyright (C) 2009-2014 Free Software Foundation, Inc.
++   Copyright (C) 2009-2013 Free Software Foundation, Inc.
+ 
+    This file is part of GDB.
+ 
+@@ -21,7 +21,6 @@
+ #include "gdbcore.h"
+ #include "target.h"
+ #include "monitor.h"
+-#include <string.h>
+ #include "serial.h"
+ #include "regcache.h"
+ 

+ 467 - 0
package/gdb-microblaze/patches/patch-gdb_microblaze-tdep_c

@@ -0,0 +1,467 @@
+--- gdb-7.8.2.orig/gdb/microblaze-tdep.c	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/microblaze-tdep.c	2016-09-21 10:34:30.029222319 +0200
+@@ -1,6 +1,6 @@
+ /* Target-dependent code for Xilinx MicroBlaze.
+ 
+-   Copyright (C) 2009-2014 Free Software Foundation, Inc.
++   Copyright (C) 2009-2013 Free Software Foundation, Inc.
+ 
+    This file is part of GDB.
+ 
+@@ -29,13 +29,13 @@
+ #include "inferior.h"
+ #include "regcache.h"
+ #include "target.h"
++#include "frame.h"
+ #include "frame-base.h"
+ #include "frame-unwind.h"
+ #include "dwarf2-frame.h"
+ #include "osabi.h"
+ 
+ #include "gdb_assert.h"
+-#include <string.h>
+ #include "target-descriptions.h"
+ #include "opcodes/microblaze-opcm.h"
+ #include "opcodes/microblaze-dis.h"
+@@ -73,7 +73,8 @@ static const char *microblaze_register_n
+   "rpc",  "rmsr", "rear", "resr", "rfsr", "rbtr",
+   "rpvr0", "rpvr1", "rpvr2", "rpvr3", "rpvr4", "rpvr5", "rpvr6",
+   "rpvr7", "rpvr8", "rpvr9", "rpvr10", "rpvr11",
+-  "redr", "rpid", "rzpr", "rtlbx", "rtlbsx", "rtlblo", "rtlbhi"
++  "redr", "rpid", "rzpr", "rtlbx", "rtlbsx", "rtlblo", "rtlbhi",
++  "rslr", "rshr"
+ };
+ 
+ #define MICROBLAZE_NUM_REGS ARRAY_SIZE (microblaze_register_names)
+@@ -145,6 +146,14 @@ microblaze_push_dummy_code (struct gdbar
+   return sp;
+ }
+ 
++static CORE_ADDR
++microblaze_store_arguments (struct regcache *regcache, int nargs,
++			    struct value **args, CORE_ADDR sp,
++			    int struct_return, CORE_ADDR struct_addr)
++{
++  error (_("store_arguments not implemented"));
++  return sp;
++}
+ 
+ static CORE_ADDR
+ microblaze_push_dummy_call (struct gdbarch *gdbarch, struct value *function,
+@@ -156,14 +165,52 @@ microblaze_push_dummy_call (struct gdbar
+   return sp;
+ }
+ 
++static int
++microblaze_linux_memory_remove_breakpoint (struct gdbarch *gdbarch,
++				    struct bp_target_info *bp_tgt)
++{
++  CORE_ADDR addr = bp_tgt->placed_address;
++  const unsigned char *bp;
++  int val;
++  int bplen;
++  gdb_byte old_contents[BREAKPOINT_MAX];
++  struct cleanup *cleanup;
++
++  /* Determine appropriate breakpoint contents and size for this address.  */
++  bp = gdbarch_breakpoint_from_pc (gdbarch, &addr, &bplen);
++  if (bp == NULL)
++    error (_("Software breakpoints not implemented for this target."));
++
++  /* Make sure we see the memory breakpoints.  */
++  cleanup = make_show_memory_breakpoints_cleanup (1);
++  val = target_read_memory (addr, old_contents, bplen);
++
++  /* If our breakpoint is no longer at the address, this means that the
++     program modified the code on us, so it is wrong to put back the
++     old value.  */
++  if (val == 0 && memcmp (bp, old_contents, bplen) == 0)
++  {
++    val = target_write_raw_memory (addr, bp_tgt->shadow_contents, bplen);
++    microblaze_debug ("microblaze_linux_memory_remove_breakpoint writing back to memory at addr 0x%lx\n", addr);
++  }
++
++  do_cleanups (cleanup);
++  return val;
++}
++
+ static const gdb_byte *
+ microblaze_breakpoint_from_pc (struct gdbarch *gdbarch, CORE_ADDR *pc, 
+ 			       int *len)
+ {
++  enum bfd_endian byte_order = gdbarch_byte_order (gdbarch);
+   static gdb_byte break_insn[] = MICROBLAZE_BREAKPOINT;
++  static gdb_byte break_insn_le[] = MICROBLAZE_BREAKPOINT_LE;
+ 
+   *len = sizeof (break_insn);
+-  return break_insn;
++  if (byte_order == BFD_ENDIAN_BIG)
++    return break_insn;
++  else
++    return break_insn_le;
+ }
+ 
+ /* Allocate and initialize a frame cache.  */
+@@ -178,6 +225,7 @@ microblaze_alloc_frame_cache (void)
+   /* Base address.  */
+   cache->base = 0;
+   cache->pc = 0;
++  cache->saved_sp = 0;
+ 
+   /* Frameless until proven otherwise.  */
+   cache->frameless_p = 1;
+@@ -234,6 +282,8 @@ microblaze_analyze_prologue (struct gdba
+   int flags = 0;
+   int save_hidden_pointer_found = 0;
+   int non_stack_instruction_found = 0;
++  int n_insns;
++  unsigned int *insn_block;
+ 
+   /* Find the start of this function.  */
+   find_pc_partial_function (pc, &name, &func_addr, &func_end);
+@@ -273,11 +323,18 @@ microblaze_analyze_prologue (struct gdba
+ 		    name, paddress (gdbarch, func_addr), 
+ 		    paddress (gdbarch, stop));
+ 
++/* Do a block read to minimize the transaction with the Debug Agent */
++  n_insns = (stop == func_addr) ? 1 : ((stop - func_addr) / INST_WORD_SIZE);
++  insn_block = calloc(n_insns, sizeof(unsigned long));
++
++  target_read_memory (func_addr, (void*) insn_block, n_insns * INST_WORD_SIZE );
++
+   for (addr = func_addr; addr < stop; addr += INST_WORD_SIZE)
+     {
+       insn = microblaze_fetch_instruction (addr);
++      //insn = insn_block[(addr - func_addr) / INST_WORD_SIZE];
+       op = microblaze_decode_insn (insn, &rd, &ra, &rb, &imm);
+-      microblaze_debug ("%s %08lx\n", paddress (gdbarch, pc), insn);
++      microblaze_debug ("%s %08lx op=%x r%d r%d imm=%d\n", paddress (gdbarch, addr), insn, op, rd, ra, imm);
+ 
+       /* This code is very sensitive to what functions are present in the
+ 	 prologue.  It assumes that the (addi, addik, swi, sw) can be the 
+@@ -291,6 +348,7 @@ microblaze_analyze_prologue (struct gdba
+ 	  cache->frameless_p = 0; /* Frame found.  */
+ 	  save_hidden_pointer_found = 0;
+ 	  non_stack_instruction_found = 0;
++	  cache->register_offsets[rd] = -imm;
+ 	  continue;
+ 	}
+       else if (IS_SPILL_SP(op, rd, ra))
+@@ -401,8 +459,8 @@ microblaze_analyze_prologue (struct gdba
+      part of the prologue.  */
+   if (save_hidden_pointer_found)
+     prologue_end_addr -= INST_WORD_SIZE;
+-
+-  return prologue_end_addr;
++    free(insn_block);
++    return prologue_end_addr;
+ }
+ 
+ static CORE_ADDR
+@@ -452,6 +510,7 @@ microblaze_skip_prologue (struct gdbarch
+   return start_pc;
+ }
+ 
++enum { REG_UNAVAIL = (CORE_ADDR) -1 };
+ /* Normal frames.  */
+ 
+ static struct microblaze_frame_cache *
+@@ -459,7 +518,7 @@ microblaze_frame_cache (struct frame_inf
+ {
+   struct microblaze_frame_cache *cache;
+   struct gdbarch *gdbarch = get_frame_arch (next_frame);
+-  CORE_ADDR func;
++  CORE_ADDR current_pc;
+   int rn;
+ 
+   if (*this_cache)
+@@ -473,9 +532,18 @@ microblaze_frame_cache (struct frame_inf
+   for (rn = 0; rn < gdbarch_num_regs (gdbarch); rn++)
+     cache->register_offsets[rn] = -1;
+ 
+-  func = get_frame_func (next_frame);
++  cache->pc = get_frame_func (next_frame);
++  current_pc = get_frame_pc (next_frame);
+ 
+-  cache->pc = get_frame_address_in_block (next_frame);
++  if (cache->pc)
++    microblaze_analyze_prologue (gdbarch, cache->pc, current_pc,
++	                         cache);
++
++  cache->base = get_frame_register_unsigned (next_frame, gdbarch_sp_regnum (gdbarch));
++  cache->saved_sp = cache->base + cache->framesize;
++
++  cache->register_offsets[MICROBLAZE_PREV_PC_REGNUM] = cache->base;
++  cache->register_offsets[MICROBLAZE_SP_REGNUM] = cache->saved_sp;
+ 
+   return cache;
+ }
+@@ -501,6 +569,14 @@ microblaze_frame_prev_register (struct f
+   struct microblaze_frame_cache *cache =
+     microblaze_frame_cache (this_frame, this_cache);
+ 
++  if ((regnum == MICROBLAZE_SP_REGNUM &&
++      cache->register_offsets[MICROBLAZE_SP_REGNUM])
++      || (regnum == MICROBLAZE_FP_REGNUM &&
++      cache->register_offsets[MICROBLAZE_SP_REGNUM]))
++
++     return frame_unwind_got_constant (this_frame, regnum,
++                                       cache->register_offsets[MICROBLAZE_SP_REGNUM]);
++
+   if (cache->frameless_p)
+     {
+       if (regnum == MICROBLAZE_PC_REGNUM)
+@@ -508,11 +584,18 @@ microblaze_frame_prev_register (struct f
+       if (regnum == MICROBLAZE_SP_REGNUM)
+         regnum = 1;
+       return trad_frame_get_prev_register (this_frame,
+-					   cache->saved_regs, regnum);
++            cache->saved_regs, regnum);
+     }
+-  else
+-    return trad_frame_get_prev_register (this_frame, cache->saved_regs,
+-					 regnum);
++
++  if (regnum == MICROBLAZE_PC_REGNUM)
++    {
++      regnum = 15;
++      return frame_unwind_got_memory (this_frame, regnum,
++                                      cache->register_offsets[MICROBLAZE_PREV_PC_REGNUM]);
++    }
++
++  return trad_frame_get_prev_register (this_frame, cache->saved_regs,
++					regnum);
+ 
+ }
+ 
+@@ -536,6 +619,12 @@ microblaze_frame_base_address (struct fr
+   return cache->base;
+ }
+ 
++static const struct frame_unwind *
++microblaze_frame_sniffer (struct frame_info *next_frame)
++{
++  return &microblaze_frame_unwind;
++}
++
+ static const struct frame_base microblaze_frame_base =
+ {
+   &microblaze_frame_unwind,
+@@ -628,6 +717,109 @@ microblaze_stabs_argument_has_addr (stru
+   return (TYPE_LENGTH (type) == 16);
+ }
+ 
++int
++microblaze_software_single_step (struct frame_info *frame)
++{
++  struct gdbarch *arch = get_frame_arch (frame);
++  struct address_space *aspace = get_frame_address_space (frame);
++  struct gdbarch_tdep *tdep = gdbarch_tdep (arch);
++  static char le_breakp[] = MICROBLAZE_BREAKPOINT_LE;
++  static char be_breakp[] = MICROBLAZE_BREAKPOINT;
++  enum bfd_endian byte_order = gdbarch_byte_order (arch);
++  char *breakp = byte_order == BFD_ENDIAN_BIG ? be_breakp : le_breakp;
++  int ret = 0;
++
++  /* Save the address and the values of the next_pc and the target */
++  static struct sstep_breaks
++  {
++    CORE_ADDR address;
++    bfd_boolean valid;
++    /* Shadow contents.  */
++    char data[INST_WORD_SIZE];
++  } stepbreaks[2];
++  int ii;
++
++  if (1)
++    {
++      CORE_ADDR pc;
++      long insn;
++      enum microblaze_instr minstr;
++      bfd_boolean isunsignednum;
++      enum microblaze_instr_type insn_type;
++      short delay_slots;
++      int imm;
++      bfd_boolean immfound = FALSE;
++
++      /* Set a breakpoint at the next instruction */
++      /* If the current instruction is an imm, set it at the inst after */
++      /* If the instruction has a delay slot, skip the delay slot */
++      pc = get_frame_pc (frame);
++      insn = microblaze_fetch_instruction (pc);
++      minstr = get_insn_microblaze (insn, &isunsignednum, &insn_type, &delay_slots);
++      if (insn_type == immediate_inst)
++	{
++	  int rd, ra, rb;
++	  immfound = TRUE;
++	  minstr = microblaze_decode_insn (insn, &rd, &ra, &rb, &imm);
++	  pc = pc + INST_WORD_SIZE;
++	  insn = microblaze_fetch_instruction (pc);
++	  minstr = get_insn_microblaze (insn, &isunsignednum, &insn_type, &delay_slots);
++	}
++      stepbreaks[0].address = pc + (delay_slots * INST_WORD_SIZE) + INST_WORD_SIZE;
++      if (insn_type != return_inst) {
++	stepbreaks[0].valid = TRUE;
++      } else {
++	stepbreaks[0].valid = FALSE;
++      }
++
++      microblaze_debug ("single-step insn_type=%x insn=%x\n", insn_type, insn);
++      /* Now check for branch or return instructions */
++      if (insn_type == branch_inst || insn_type == return_inst) {
++	int limm;
++	int lrd, lra, lrb;
++	int ra, rb;
++	bfd_boolean targetvalid;
++	bfd_boolean unconditionalbranch;
++	microblaze_decode_insn(insn, &lrd, &lra, &lrb, &limm);
++	if (lra >= 0 && lra < MICROBLAZE_NUM_REGS)
++	  ra = get_frame_register_unsigned (frame, lra);
++	else
++	  ra = 0;
++	if (lrb >= 0 && lrb < MICROBLAZE_NUM_REGS)
++	  rb = get_frame_register_unsigned (frame, lrb);
++	else
++	  rb = 0;
++
++	stepbreaks[1].address = microblaze_get_target_address (insn, immfound, imm, pc, ra, rb, &targetvalid, &unconditionalbranch);
++	microblaze_debug ("single-step uncondbr=%d targetvalid=%d target=%x\n", unconditionalbranch, targetvalid, stepbreaks[1].address);
++
++	if (unconditionalbranch)
++	  stepbreaks[0].valid = FALSE; /* This is a unconditional branch: will not come to the next address */
++	if (targetvalid && (stepbreaks[0].valid == FALSE ||
++			    (stepbreaks[0].address != stepbreaks[1].address))
++			&& (stepbreaks[1].address != pc)) {
++	  stepbreaks[1].valid = TRUE;
++	} else {
++	  stepbreaks[1].valid = FALSE;
++	}
++      } else {
++	stepbreaks[1].valid = FALSE;
++      }
++
++      /* Insert the breakpoints */
++      for (ii = 0; ii < 2; ++ii)
++        {
++
++          /* ignore invalid breakpoint. */
++          if (stepbreaks[ii].valid) {
++            insert_single_step_breakpoint (arch, aspace, stepbreaks[ii].address);
++            ret = 1;
++	  }
++	}
++    }
++    return ret;
++}
++
+ static void
+ microblaze_write_pc (struct regcache *regcache, CORE_ADDR pc)
+ {
+@@ -664,6 +856,70 @@ microblaze_dwarf2_reg_to_regnum (struct
+   return dwarf2_to_reg_map[reg];
+ }
+ 
++
++void
++microblaze_supply_gregset (const struct microblaze_gregset *gregset,
++                        struct regcache *regcache,
++                        int regnum, const void *gregs)
++{
++  unsigned int *regs = gregs;
++  if (regnum >= 0)
++    regcache_raw_supply (regcache, regnum, regs + regnum);
++
++  if (regnum == -1) {
++    int i;
++
++    for (i = 0; i < 50; i++) {
++      regcache_raw_supply (regcache, i, regs + i);
++    }
++  }
++}
++
++
++void
++microblaze_collect_gregset (const struct microblaze_gregset *gregset,
++                         const struct regcache *regcache,
++                         int regnum, void *gregs)
++{
++   /* FIXME.  */
++}
++
++void
++microblaze_supply_fpregset (struct regcache *regcache,
++                         int regnum, const void *fpregs)
++{
++   /* FIXME.  */
++}
++
++void
++microblaze_collect_fpregset (const struct regcache *regcache,
++                          int regnum, void *fpregs)
++{
++   /* FIXME.  */
++}
++
++
++/* Return the appropriate register set for the core section identified
++   by SECT_NAME and SECT_SIZE.  */
++
++const struct regset *
++microblaze_regset_from_core_section (struct gdbarch *gdbarch,
++                                     const char *sect_name, size_t sect_size)
++{
++  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
++
++  microblaze_debug ("microblaze_regset_from_core_section, sect_name = %s\n", sect_name);
++
++  if (strcmp (sect_name, ".reg") == 0 && sect_size >= tdep->sizeof_gregset)
++    return tdep->gregset;
++
++  if (strcmp (sect_name, ".reg2") == 0 && sect_size >= tdep->sizeof_fpregset)
++    return tdep->fpregset;
++
++  microblaze_debug ("microblaze_regset_from_core_section returning null :-( \n");
++  return NULL;
++}
++
+ static struct gdbarch *
+ microblaze_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
+ {
+@@ -679,6 +935,11 @@ microblaze_gdbarch_init (struct gdbarch_
+   tdep = XNEW (struct gdbarch_tdep);
+   gdbarch = gdbarch_alloc (&info, tdep);
+ 
++  tdep->gregset = NULL;
++  tdep->sizeof_gregset = 0;
++  tdep->fpregset = NULL;
++  tdep->sizeof_fpregset = 0;
++
+   set_gdbarch_long_double_bit (gdbarch, 128);
+ 
+   set_gdbarch_num_regs (gdbarch, MICROBLAZE_NUM_REGS);
+@@ -706,7 +967,10 @@ microblaze_gdbarch_init (struct gdbarch_
+   /* Stack grows downward.  */
+   set_gdbarch_inner_than (gdbarch, core_addr_lessthan);
+ 
++  set_gdbarch_memory_remove_breakpoint (gdbarch, microblaze_linux_memory_remove_breakpoint);
++
+   set_gdbarch_breakpoint_from_pc (gdbarch, microblaze_breakpoint_from_pc);
++  set_gdbarch_software_single_step (gdbarch, microblaze_software_single_step);
+ 
+   set_gdbarch_frame_args_skip (gdbarch, 8);
+ 
+@@ -725,6 +989,13 @@ microblaze_gdbarch_init (struct gdbarch_
+   dwarf2_append_unwinders (gdbarch);
+   frame_unwind_append_unwinder (gdbarch, &microblaze_frame_unwind);
+   frame_base_append_sniffer (gdbarch, dwarf2_frame_base_sniffer);
++  //frame_base_append_sniffer (gdbarch, microblaze_frame_sniffer);
++
++  /* If we have register sets, enable the generic core file support.  */
++  if (tdep->gregset) {
++      set_gdbarch_regset_from_core_section (gdbarch,
++                                          microblaze_regset_from_core_section);
++  }
+ 
+   return gdbarch;
+ }

+ 91 - 0
package/gdb-microblaze/patches/patch-gdb_microblaze-tdep_h

@@ -0,0 +1,91 @@
+--- gdb-7.8.2.orig/gdb/microblaze-tdep.h	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/gdb/microblaze-tdep.h	2016-09-21 10:34:30.029222319 +0200
+@@ -1,6 +1,6 @@
+ /* Target-dependent code for Xilinx MicroBlaze.
+ 
+-   Copyright (C) 2009-2014 Free Software Foundation, Inc.
++   Copyright (C) 2009-2013 Free Software Foundation, Inc.
+ 
+    This file is part of GDB.
+ 
+@@ -22,8 +22,22 @@
+ 
+ 
+ /* Microblaze architecture-specific information.  */
++struct microblaze_gregset
++{
++   unsigned int gregs[32];
++   unsigned int fpregs[32];
++   unsigned int pregs[16];
++};
++
+ struct gdbarch_tdep
+ {
++  int dummy;		// declare something.
++
++  /* Register sets.  */
++  struct regset *gregset;
++  size_t sizeof_gregset;
++  struct regset *fpregset;
++  size_t sizeof_fpregset;
+ };
+ 
+ struct microblaze_frame_cache
+@@ -42,7 +56,8 @@ struct microblaze_frame_cache
+   int fp_regnum;
+ 
+   /* Offsets to saved registers.  */
+-  int register_offsets[57];	/* Must match MICROBLAZE_NUM_REGS.  */
++  int register_offsets[59];	/* Must match MICROBLAZE_NUM_REGS.  */
++  CORE_ADDR saved_sp;
+ 
+   /* Table of saved registers.  */
+   struct trad_frame_saved_reg *saved_regs;
+@@ -66,11 +81,11 @@ enum microblaze_regnum
+   MICROBLAZE_R12_REGNUM,
+   MICROBLAZE_R13_REGNUM,
+   MICROBLAZE_R14_REGNUM,
+-  MICROBLAZE_R15_REGNUM,
++  MICROBLAZE_R15_REGNUM, MICROBLAZE_PREV_PC_REGNUM = MICROBLAZE_R15_REGNUM,
+   MICROBLAZE_R16_REGNUM,
+   MICROBLAZE_R17_REGNUM,
+   MICROBLAZE_R18_REGNUM,
+-  MICROBLAZE_R19_REGNUM,
++  MICROBLAZE_R19_REGNUM, MICROBLAZE_FP_REGNUM = MICROBLAZE_R19_REGNUM,
+   MICROBLAZE_R20_REGNUM,
+   MICROBLAZE_R21_REGNUM,
+   MICROBLAZE_R22_REGNUM,
+@@ -107,7 +122,9 @@ enum microblaze_regnum
+   MICROBLAZE_RTLBX_REGNUM,
+   MICROBLAZE_RTLBSX_REGNUM,
+   MICROBLAZE_RTLBLO_REGNUM,
+-  MICROBLAZE_RTLBHI_REGNUM
++  MICROBLAZE_RTLBHI_REGNUM,
++  MICROBLAZE_SLR_REGNUM,
++  MICROBLAZE_SHR_REGNUM
+ };
+ 
+ /* All registers are 32 bits.  */
+@@ -115,6 +132,21 @@ enum microblaze_regnum
+ 
+ /* MICROBLAZE_BREAKPOINT defines the breakpoint that should be used.
+    Only used for native debugging.  */
+-#define MICROBLAZE_BREAKPOINT {0xb9, 0xcc, 0x00, 0x60}
++#define MICROBLAZE_BREAKPOINT {0xba, 0x0c, 0x00, 0x18}
++#define MICROBLAZE_BREAKPOINT_LE {0x18, 0x00, 0x0c, 0xba}
++
++extern void microblaze_supply_gregset (const struct microblaze_gregset *gregset,
++                                    struct regcache *regcache,
++                                    int regnum, const void *gregs);
++extern void microblaze_collect_gregset (const struct microblaze_gregset *gregset,
++                                     const struct regcache *regcache,
++                                     int regnum, void *gregs);
++extern void microblaze_supply_fpregset (struct regcache *regcache,
++                                     int regnum, const void *fpregs);
++extern void microblaze_collect_fpregset (const struct regcache *regcache,
++                                      int regnum, void *fpregs);
++
++extern const struct regset * microblaze_regset_from_core_section (struct gdbarch *gdbarch,
++                                     const char *sect_name, size_t sect_size);
+ 
+ #endif /* microblaze-tdep.h */

+ 44 - 0
package/gdb-microblaze/patches/patch-gdb_regformats_reg-microblaze_dat

@@ -0,0 +1,44 @@
+--- gdb-7.8.2.orig/gdb/regformats/reg-microblaze.dat	1970-01-01 00:00:00.000000000 +0100
++++ gdb-7.8.2/gdb/regformats/reg-microblaze.dat	2016-09-21 10:34:30.029222319 +0200
+@@ -0,0 +1,41 @@
++name:microblaze
++expedite:r1,pc
++32:r0
++32:r1
++32:r2
++32:r3
++32:r4
++32:r5
++32:r6
++32:r7
++32:r8
++32:r9
++32:r10
++32:r11
++32:r12
++32:r13
++32:r14
++32:r15
++32:r16
++32:r17
++32:r18
++32:r19
++32:r20
++32:r21
++32:r22
++32:r23
++32:r24
++32:r25
++32:r26
++32:r27
++32:r28
++32:r29
++32:r30
++32:r31
++32:pc
++32:msr
++32:ear
++32:esr
++32:fsr
++32:slr
++32:shr

+ 33 - 0
package/gdb-microblaze/patches/patch-gdb_sgidefs_h

@@ -0,0 +1,33 @@
+--- gdb-7.8.2.orig/gdb/sgidefs.h	1970-01-01 00:00:00.000000000 +0100
++++ gdb-7.8.2/gdb/sgidefs.h	2016-09-20 19:56:32.003878822 +0200
+@@ -0,0 +1,30 @@
++#ifndef _SGIDEFS_H
++#define _SGIDEFS_H
++
++/* MIPS ABI crap that GLIBC puts into /include
++by default, and GDB depends on it happily. */
++
++#define _MIPS_ISA_MIPS1 1
++#define _MIPS_ISA_MIPS2 2
++#define _MIPS_ISA_MIPS3 3
++#define _MIPS_ISA_MIPS4 4
++#define _MIPS_ISA_MIPS5 5
++#define _MIPS_ISA_MIPS32 6
++#define _MIPS_ISA_MIPS64 7
++
++#ifndef _ABIO32
++#define _ABIO32 1
++#endif
++#define _MIPS_SIM_ABI32 _ABIO32
++
++#ifndef _ABIN32
++#define _ABIN32 2
++#endif
++#define _MIPS_SIM_NABI32 _ABIN32
++
++#ifndef _ABI64
++#define _ABI64 3
++#endif
++#define _MIPS_SIM_ABI64 _ABI64
++
++#endif

+ 10 - 0
package/gdb-microblaze/patches/patch-include_elf_microblaze_h

@@ -0,0 +1,10 @@
+--- gdb-7.8.2.orig/include/elf/microblaze.h	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/include/elf/microblaze.h	2016-09-21 10:34:30.029222319 +0200
+@@ -58,6 +58,7 @@ START_RELOC_NUMBERS (elf_microblaze_relo
+   RELOC_NUMBER (R_MICROBLAZE_TLSDTPREL64, 27)   /* TLS Offset Within TLS Block */
+   RELOC_NUMBER (R_MICROBLAZE_TLSGOTTPREL32, 28) /* TLS Offset From Thread Pointer */
+   RELOC_NUMBER (R_MICROBLAZE_TLSTPREL32, 29)    /* TLS Offset From Thread Pointer */
++  RELOC_NUMBER (R_MICROBLAZE_32_NONE, 30)
+    
+ END_RELOC_NUMBERS (R_MICROBLAZE_max)
+ 

+ 29 - 0
package/gdb-microblaze/patches/patch-opcodes_microblaze-opc_h

@@ -0,0 +1,29 @@
+--- gdb-7.8.2.orig/opcodes/microblaze-opc.h	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/opcodes/microblaze-opc.h	2016-09-21 10:34:30.029222319 +0200
+@@ -91,6 +91,7 @@
+ #define OPCODE_MASK_H3  0xFC000600  /* High 6 bits and bits 21, 22.  */  
+ #define OPCODE_MASK_H32 0xFC00FC00  /* High 6 bits and bit 16-21.  */
+ #define OPCODE_MASK_H34B 0xFC0000FF /* High 6 bits and low 8 bits.  */
++#define OPCODE_MASK_H35B 0xFC0004FF /* High 6 bits and low 9 bits.  */
+ #define OPCODE_MASK_H34C 0xFC0007E0 /* High 6 bits and bits 21-26.  */
+ 
+ /* New Mask for msrset, msrclr insns.  */
+@@ -101,7 +102,7 @@
+ #define DELAY_SLOT 1
+ #define NO_DELAY_SLOT 0
+ 
+-#define MAX_OPCODES 289
++#define MAX_OPCODES 291
+ 
+ struct op_code_struct
+ {
+@@ -174,7 +175,9 @@ struct op_code_struct
+   {"wic",   INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000068, OPCODE_MASK_H34B, wic, special_inst },
+   {"wdc",   INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000064, OPCODE_MASK_H34B, wdc, special_inst },
+   {"wdc.clear", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000066, OPCODE_MASK_H34B, wdcclear, special_inst },
++  {"wdc.ext.clear", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000466, OPCODE_MASK_H35B, wdcextclear, special_inst },
+   {"wdc.flush", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000074, OPCODE_MASK_H34B, wdcflush, special_inst },
++  {"wdc.ext.flush", INST_TYPE_R1_R2_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x90000476, OPCODE_MASK_H35B, wdcextflush, special_inst },
+   {"mts",   INST_TYPE_SPECIAL_R1, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_MTS, 0x9400C000, OPCODE_MASK_H13S, mts, special_inst },
+   {"mfs",   INST_TYPE_RD_SPECIAL, INST_NO_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_MFS, 0x94008000, OPCODE_MASK_H23S, mfs, special_inst },
+   {"br",    INST_TYPE_R2, INST_PC_OFFSET, NO_DELAY_SLOT, IMMVAL_MASK_NON_SPECIAL, 0x98000000, OPCODE_MASK_H124, br, branch_inst },

+ 15 - 0
package/gdb-microblaze/patches/patch-opcodes_microblaze-opcm_h

@@ -0,0 +1,15 @@
+--- gdb-7.8.2.orig/opcodes/microblaze-opcm.h	2015-01-15 11:58:12.000000000 +0100
++++ gdb-7.8.2/opcodes/microblaze-opcm.h	2016-09-21 10:34:30.029222319 +0200
+@@ -31,9 +31,9 @@ enum microblaze_instr
+   idiv, idivu, bsll, bsra, bsrl, get, put, nget, nput, cget, cput,
+   ncget, ncput, muli, bslli, bsrai, bsrli, mului, or, and, xor,
+   andn, pcmpbf, pcmpbc, pcmpeq, pcmpne, sra, src, srl, sext8, sext16, 
+-  wic, wdc, wdcclear, wdcflush, mts, mfs, mbar, br, brd,
+-  brld, bra, brad, brald, microblaze_brk, beq, beqd, bne, bned, blt,
+-  bltd, ble, bled, bgt, bgtd, bge, bged, ori, andi, xori, andni,
++  wic, wdc, wdcclear, wdcextclear, wdcflush, wdcextflush, mts, mfs, mbar,
++  br, brd, brld, bra, brad, brald, microblaze_brk, beq, beqd, bne, bned,
++  blt, bltd, ble, bled, bgt, bgtd, bge, bged, ori, andi, xori, andni,
+   imm, rtsd, rtid, rtbd, rted, bri, brid, brlid, brai, braid, bralid,
+   brki, beqi, beqid, bnei, bneid, blti, bltid, blei, bleid, bgti,
+   bgtid, bgei, bgeid, lbu, lbur, lhu, lhur, lw, lwr, lwx, sb, sbr, sh,