--- ./gdb/rs6000-nat.c_orig	2017-02-05 21:52:08 -0600
+++ ./gdb/rs6000-nat.c	2017-02-05 21:32:15 -0600
@@ -36,6 +36,7 @@
 #include "exec.h"
 #include "observer.h"
 #include "xcoffread.h"
+#include "gdbthread.h"
 
 #include <sys/ptrace.h>
 #include <sys/reg.h>
@@ -55,6 +56,18 @@
 #define __LDINFO_PTRACE64__	/* for __ld_info64 */
 #include <sys/ldr.h>
 #include <sys/systemcfg.h>
+#include <sys/context.h>
+#include <sys/pthdebug.h>
+
+#include "features/rs6000/powerpc-vsx64.c"
+#include "features/rs6000/powerpc-vsx32.c"
+#include "features/rs6000/powerpc-altivec32.c"
+#include "features/rs6000/powerpc-altivec64.c"
+
+
+int have_ptrace_getvrregs = 1;
+
+int have_ptrace_getsetvsxregs = 1;
 
 /* On AIX4.3+, sys/ldr.h provides different versions of struct ld_info for
    debugging 32-bit and 64-bit processes.  Define a typedef and macros for
@@ -217,6 +230,86 @@
     }
 }
 
+static void
+store_vsx_register_aix (struct regcache *regcache, int regno)
+{
+  int ret;
+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+  int vsxregsize = register_size (gdbarch, tdep->ppc_vsr0_upper_regnum);
+  struct thrdentry64 thrdentry;
+  __vsx_context_t vsx;
+  pid_t pid = ptid_get_pid (inferior_ptid);
+  tid64_t  thrd_i = 0;
+
+  if (getthrds64(pid, &thrdentry, sizeof(struct thrdentry64),
+               &thrd_i, 1) == 1)
+    thrd_i = thrdentry.ti_tid;
+  memset(&vsx, 0, sizeof(__vsx_context_t));
+  if (__power_vsx())  {
+    ret = ptrace64 (PTT_READ_VSX, thrd_i, (long long) &vsx, 0, 0);
+    if (ret < 0)
+    {
+       if (errno == ENXIO)
+       {
+         /* have_ptrace_getsetvsxregs = 0; */
+         warning (_("Unable to fetch VSX registers."));
+         return;
+       }
+    }
+  }
+  regcache_raw_collect (regcache, regno, &(vsx.__vsr_dw1[0])+
+                       regno - tdep->ppc_vsr0_upper_regnum);
+
+  ret = ptrace64 (PTT_WRITE_VSX, thrd_i, (long long) &vsx, 0, 0);
+  if (ret < 0)
+    perror_with_name (_("Unable to store VSX register."));
+
+}
+
+static void
+store_altivec_register_aix (struct regcache *regcache, int regno)
+{
+  int offset = 0;
+  int ret;
+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+  int vrregsize = register_size (gdbarch, tdep->ppc_vr0_regnum);
+  struct thrdentry64 thrdentry;
+  __vmx_context_t vmx;
+  pid_t pid = ptid_get_pid (inferior_ptid);
+  tid64_t  thrd_i = 0;
+
+  if (getthrds64(pid, &thrdentry, sizeof(struct thrdentry64),
+               &thrd_i, 1) == 1)
+    thrd_i = thrdentry.ti_tid;
+  memset(&vmx, 0, sizeof(__vmx_context_t));
+  if (__power_vmx())  {
+    ret = ptrace64 (PTT_READ_VEC, thrd_i, (long long) &vmx, 0, 0);
+    if (ret < 0)
+    {
+       if (errno == ENXIO)
+       {
+         /* have_ptrace_getvrregs = 0; */
+         warning (_("Unable to fetch AltiVec registers."));
+         return;
+       }
+    }
+  }   
+    /* VSCR is fetched as a 16 bytes quantity, but it is really 4 bytes
+     long on the hardware.  */
+  if (regno == (tdep->ppc_vrsave_regnum - 1))
+    offset = vrregsize - register_size (gdbarch, tdep->ppc_vrsave_regnum);
+
+  regcache_raw_collect (regcache, regno, &(vmx.__vr[0]) + regno
+                                - tdep->ppc_vr0_regnum);
+
+  ret = ptrace64 (PTT_WRITE_VEC, thrd_i, (long long) &vmx, 0, 0);
+  if (ret < 0)
+     perror_with_name (_("Unable to store AltiVec register."));
+
+}
+
 /* Store register REGNO back into the inferior.  */
 
 static void
@@ -270,6 +363,17 @@
 	}
     }
 
+   if (altivec_register_p (gdbarch, regno))
+   {
+     store_altivec_register_aix (regcache, regno);
+     return;
+   }
+   if (vsx_register_p (gdbarch, regno))
+   {
+     store_vsx_register_aix (regcache, regno);
+     return;
+   }
+
   if (errno)
     {
       perror (_("ptrace write"));
@@ -277,6 +381,112 @@
     }
 }
 
+static void
+supply_vsxregset_aix (struct regcache *regcache, __vsx_context_t *vsx)
+{
+
+  int i;
+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+  int vsxregsize = register_size (gdbarch, tdep->ppc_vsr0_upper_regnum);
+
+
+    for (i = 0; i < ppc_num_vshrs; i++)
+    {
+        regcache_raw_supply (regcache, tdep->ppc_vsr0_upper_regnum + i,
+                             &(vsx->__vsr_dw1[i]));
+    }
+}
+
+static void
+fetch_vsx_registers_aix (struct regcache *regcache)
+{
+  int ret;
+  struct thrdentry64 thrdentry;
+  __vsx_context_t vsx;
+  pid_t pid = ptid_get_pid (inferior_ptid);
+  tid64_t  thrd_i = 0;
+
+  if (getthrds64(pid, &thrdentry, sizeof(struct thrdentry64),
+               &thrd_i, 1) == 1)
+    thrd_i = thrdentry.ti_tid;
+  memset(&vsx, 0, sizeof(__vsx_context_t));
+  if (__power_vsx())  {
+    ret = ptrace64 (PTT_READ_VSX, thrd_i, (long long) &vsx, 0, 0);
+    if (ret < 0)
+    {
+       /* Just fill with 0 zero instead of error return */
+       #if 0
+         if (errno == ENXIO)
+         {
+           have_ptrace_getsetvsxregs = 0;
+           return;
+           perror_with_name (_("Unable to fetch VSX registers"));
+         }
+       #endif
+    }
+  }
+  supply_vsxregset_aix (regcache, &vsx);
+}
+
+
+static void
+supply_vrregset_aix (struct regcache *regcache, __vmx_context_t *vmx)
+{
+  int i;
+  struct gdbarch *gdbarch = get_regcache_arch (regcache);
+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+  int num_of_vrregs = tdep->ppc_vrsave_regnum - tdep->ppc_vr0_regnum + 1;
+  int vrregsize = register_size (gdbarch, tdep->ppc_vr0_regnum);
+  int offset = vrregsize - register_size (gdbarch, tdep->ppc_vrsave_regnum);
+
+  for (i = 0; i < num_of_vrregs; i++)
+    {
+      /* The last 2 registers of this set are only 32 bit long, not
+         128.  However an offset is necessary only for VSCR because it
+         occupies a whole vector, while VRSAVE occupies a full 4 bytes
+         slot.  */
+      if (i == (num_of_vrregs - 2))
+        regcache_raw_supply (regcache, tdep->ppc_vr0_regnum + i,
+                             &(vmx->__vr[i]));
+      else
+        regcache_raw_supply (regcache, tdep->ppc_vr0_regnum + i,
+                             &(vmx->__vr[i]));
+    }
+}
+
+static void
+fetch_altivec_registers_aix (struct regcache *regcache)
+{
+  int ret;
+  struct thrdentry64 thrdentry;
+  __vmx_context_t vmx;
+  pid_t pid = ptid_get_pid (inferior_ptid);
+  tid64_t  thrd_i = 0;
+
+  if (getthrds64(pid, &thrdentry, sizeof(struct thrdentry64),
+                               &thrd_i, 1) == 1)
+    thrd_i = thrdentry.ti_tid;
+
+  memset(&vmx, 0, sizeof(__vmx_context_t));
+  if (__power_vmx())  {
+    ret = ptrace64 (PTT_READ_VEC, thrd_i, (long long) &vmx, 0, 0);
+    if (ret < 0)
+    {
+       /* Just fill with 0 zero instead of error return */
+       #if 0
+         if (errno == ENXIO)
+         {
+           have_ptrace_getvrregs = 0;
+           return;
+           perror_with_name (_("Unable to fetch AltiVec registers"));
+         }
+       #endif
+    }
+  }   
+  supply_vrregset_aix (regcache, &vmx);
+}   
+
 /* Read from the inferior all registers if REGNO == -1 and just register
    REGNO otherwise.  */
 
@@ -285,11 +495,7 @@
 				 struct regcache *regcache, int regno)
 {
   struct gdbarch *gdbarch = get_regcache_arch (regcache);
-  if (regno != -1)
-    fetch_register (regcache, regno);
-
-  else
-    {
+  {
       struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
 
       /* Read 32 general purpose registers.  */
@@ -316,6 +522,18 @@
         fetch_register (regcache, tdep->ppc_fpscr_regnum);
       if (tdep->ppc_mq_regnum >= 0)
 	fetch_register (regcache, tdep->ppc_mq_regnum);
+
+      if (have_ptrace_getvrregs)
+        if (tdep->ppc_vr0_regnum != -1 && tdep->ppc_vrsave_regnum != -1) 
+        {
+           fetch_altivec_registers_aix (regcache);
+        }
+
+      if (have_ptrace_getsetvsxregs)
+         if (tdep->ppc_vsr0_upper_regnum != -1)
+          {
+            fetch_vsx_registers_aix (regcache);
+          }
     }
 }
 
@@ -656,7 +874,17 @@
     }
 }
 
-void _initialize_rs6000_nat (void);
+static const struct target_desc *
+rs6000_read_description (struct target_ops *ops)
+{
+   if (ARCH64())
+      return tdesc_powerpc_vsx64;
+   else
+      return tdesc_powerpc_vsx32;
+}
+
+
+void _ixnitialize_rs6000_nar (void);
 
 void
 _initialize_rs6000_nat (void)
@@ -672,6 +900,7 @@
   t->to_create_inferior = rs6000_create_inferior;
 
   t->to_wait = rs6000_wait;
+  t->to_read_description = rs6000_read_description;
 
   add_target (t);
 }
--- ./gdb/rs6000-tdep.c_orig	2017-02-05 21:53:27 -0600
+++ ./gdb/rs6000-tdep.c	2017-02-04 08:38:50 -0600
@@ -599,12 +599,12 @@
 
   if (regnum == -1)
     {
-      int i;
+      int i, offset = 0;
 
       for (i = tdep->ppc_vsr0_upper_regnum;
 	   i < tdep->ppc_vsr0_upper_regnum + 32;
-	   i++)
-	ppc_supply_reg (regcache, i, vsxregs, 0, 8);
+	   i++, offset++)
+	ppc_supply_reg (regcache, i, vsxregs, offset * 8, 8);
 
       return;
     }
@@ -1913,8 +1913,10 @@
 	 stack.  */
       /* 001110 00000 00000 iiii iiii iiii iiii  */
       /* 001110 01110 00000 iiii iiii iiii iiii  */
+      /* TODO-AIX: Need some more  improvment */
       else if ((op & 0xffff0000) == 0x38000000         /* li r0, SIMM */
-               || (op & 0xffff0000) == 0x39c00000)     /* li r14, SIMM */
+               || (op & 0xffff0000) == 0x39c00000      /* li r14, SIMM */
+               || (op & 0xff0f0000) == 0x38000000)     /* li, r4, SIMM */
 	{
           if ((op & 0xffff0000) == 0x38000000)
             r0_contains_arg = 0;
@@ -1928,23 +1930,21 @@
 	}
       /* Store vector register S at (r31+r0) aligned to 16 bytes.  */      
       /* 011111 sssss 11111 00000 00111001110 */
-      else if ((op & 0xfc1fffff) == 0x7c1f01ce)   /* stvx Vs, R31, R0 */
+      /* TODO-AIX: Need some more  improvment */
+      else if ((op & 0xfc1fffff) == 0x7c1f01ce    /* stvx Vs, R31, R0 */
+               || (op & 0xfc1fffff) == 0x7c012f99 /* stxvd2x Vs,r1, r5 */
+               || (op & 0xfc1fffff) == 0x7c012f98 /* stxvd2x vs0, r1, r5 */
+               || (op & 0xfc1ff000) == 0x7c012000)
         {
-	  if (pc == (li_found_pc + 4))
-	    {
 	      vr_reg = GET_SRC_REG (op);
 	      /* If this is the first vector reg to be saved, or if
 		 it has a lower number than others previously seen,
 		 reupdate the frame info.  */
-	      if (fdata->saved_vr == -1 || fdata->saved_vr > vr_reg)
-		{
-		  fdata->saved_vr = vr_reg;
-		  fdata->vr_offset = vr_saved_offset + offset;
-		}
+	      fdata->saved_vr = vr_reg;
+	      fdata->vr_offset = vr_saved_offset;
 	      vr_saved_offset = -1;
 	      vr_reg = -1;
 	      li_found_pc = 0;
-	    }
 	}
       /* End AltiVec related instructions.  */
 
@@ -3041,7 +3041,7 @@
   {"powerpc", "PowerPC user-level", bfd_arch_powerpc,
    bfd_mach_ppc, &tdesc_powerpc_altivec32},
   {"power", "POWER user-level", bfd_arch_rs6000,
-   bfd_mach_rs6k, &tdesc_rs6000},
+   bfd_mach_rs6k, &tdesc_powerpc_vsx32},
   {"403", "IBM PowerPC 403", bfd_arch_powerpc,
    bfd_mach_ppc_403, &tdesc_powerpc_403},
   {"405", "IBM PowerPC 405", bfd_arch_powerpc,
@@ -3071,7 +3071,7 @@
   {"powerpc64", "PowerPC 64-bit user-level", bfd_arch_powerpc,
    bfd_mach_ppc64, &tdesc_powerpc_altivec64},
   {"620", "Motorola PowerPC 620", bfd_arch_powerpc,
-   bfd_mach_ppc_620, &tdesc_powerpc_64},
+  bfd_mach_ppc_620, &tdesc_powerpc_vsx64},
   {"630", "Motorola PowerPC 630", bfd_arch_powerpc,
    bfd_mach_ppc_630, &tdesc_powerpc_64},
   {"a35", "PowerPC A35", bfd_arch_powerpc,
@@ -3293,18 +3293,16 @@
 
   /* if != -1, fdata.saved_vr is the smallest number of saved_vr.
      All vr's from saved_vr to vr31 are saved.  */
+  /* TODO-AIX: Need some more  improvment */
   if (tdep->ppc_vr0_regnum != -1 && tdep->ppc_vrsave_regnum != -1)
     {
-      if (fdata.saved_vr >= 0)
-	{
-	  int i;
-	  CORE_ADDR vr_addr = cache->base + fdata.vr_offset;
-	  for (i = fdata.saved_vr; i < 32; i++)
-	    {
-	      cache->saved_regs[tdep->ppc_vr0_regnum + i].addr = vr_addr;
-	      vr_addr += register_size (gdbarch, tdep->ppc_vr0_regnum);
-	    }
-	}
+          int i;
+          CORE_ADDR vr_addr = cache->base + fdata.vr_offset;
+          for (i = 0; i < 66; i++)
+          {
+            cache->saved_regs[tdep->ppc_vsr0_upper_regnum + i].addr = vr_addr;
+            vr_addr += register_size (gdbarch, tdep->ppc_vsr0_upper_regnum);
+          }
     }
 
   /* if != -1, fdata.saved_ev is the smallest number of saved_ev.
--- ./gdb/aix-thread.c_orig	2017-02-05 21:54:34 -0600
+++ ./gdb/aix-thread.c	2017-02-05 21:31:43 -0600
@@ -55,6 +55,7 @@
 #include <sys/reg.h>
 #include <sched.h>
 #include <sys/pthdebug.h>
+#include <sys/context.h>
 
 #if !HAVE_DECL_GETTHRDS
 extern int getthrds (pid_t, struct thrdsinfo64 *, int, tid_t *, int);
@@ -1295,6 +1296,55 @@
 				 (char *) &sprs32.pt_mq);
 	}
     }
+    /* vector registers */
+    if (tdep->ppc_vr0_regnum != -1 && regno >= tdep->ppc_vr0_regnum)
+    {
+       int ret = 0;
+       int i = 0;
+       int num_of_vrregs = tdep->ppc_vrsave_regnum - tdep->ppc_vr0_regnum + 1;
+       __vmx_context_t vmx;
+       memset(&vmx, 0, sizeof(__vmx_context_t)); 
+       if (__power_vmx())  {
+          ret = ptrace64 (PTT_READ_VEC, tid, (long long) &vmx, 0, 0);
+          if (ret < 0)
+          {
+            /* Just fill with 0 zero instead of error return */
+             #if 0
+               if (errno == ENXIO)
+                 return;
+               perror_with_name (_("Unable to fetch AltiVec registers"));
+             #endif
+          }   
+         for (i = 0; i < num_of_vrregs; i++)
+         {
+             regcache_raw_supply (regcache, tdep->ppc_vr0_regnum + i, 
+                                  &(vmx.__vr[i]));
+         }   
+       }
+    }
+    /* vsx registers */
+    if (tdep->ppc_vsr0_upper_regnum != -1 && regno >= tdep->ppc_vsr0_upper_regnum) {
+       __vsx_context_t vsx;
+       memset(&vsx, 0, sizeof(__vsx_context_t)); 
+       if (__power_vsx())  {
+           int i = 0, ret = 0;
+           ret = ptrace64 (PTT_READ_VSX, tid, (long long) &vsx, 0, 0);
+           if (ret < 0)
+           {
+             /* Just fill with zeros instead of error return */
+             #if 0
+               if (errno == ENXIO)
+                 return;
+               perror_with_name (_("Unable to fetch VSX registers"));
+             #endif
+           }
+           for (i = 0; i < ppc_num_vshrs; i++)
+               regcache_raw_supply (regcache, tdep->ppc_vsr0_upper_regnum + i,
+                                    &(vsx.__vsr_dw1[i]));
+       } 
+ 
+    }
+
 }
 
 /* Fetch register REGNO if != -1 or all registers otherwise in the
@@ -1538,6 +1588,34 @@
            pd_status2str (status));
 }
 
+static void
+fill_altivec (const struct regcache *regcache, __vmx_context_t *vmx)
+{
+  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
+  int num_of_vrregs = tdep->ppc_vrsave_regnum - tdep->ppc_vr0_regnum + 1;
+  int regno;
+
+  for (regno = 0; regno < num_of_vrregs; regno++)
+    if (REG_VALID == regcache_register_status (regcache,
+                                               tdep->ppc_vr0_regnum + regno))
+      regcache_raw_collect (regcache, tdep->ppc_vr0_regnum + regno,
+                            &(vmx->__vr[0]) + regno);
+}
+
+static void
+fill_vsx (const struct regcache *regcache, __vsx_context_t  *vsx)
+{
+  struct gdbarch_tdep *tdep = gdbarch_tdep (get_regcache_arch (regcache));
+  int num_of_vrregs = tdep->ppc_vrsave_regnum - tdep->ppc_vr0_regnum + 1;
+  int regno;
+
+  for (regno = 0; regno < ppc_num_vshrs; regno++)
+    if (REG_VALID == regcache_register_status (regcache,
+                                               tdep->ppc_vsr0_upper_regnum + regno))
+      regcache_raw_collect (regcache, tdep->ppc_vsr0_upper_regnum + regno,
+                            &(vsx->__vsr_dw1[0]) + regno);
+}
+
 /* Store register REGNO if != -1 or all registers otherwise into
    kernel thread TID.
 
@@ -1649,6 +1727,50 @@
 	  ptrace32 (PTT_WRITE_SPRS, tid, (uintptr_t) &sprs32, 0, NULL);
 	}
     }
+    /* vector register */
+    if (tdep->ppc_vr0_regnum != -1 && regno >= tdep->ppc_vr0_regnum)
+    {
+       int ret = 0;
+       int i = 0;
+       int num_of_vrregs = tdep->ppc_vrsave_regnum - tdep->ppc_vr0_regnum + 1;
+       __vmx_context_t vmx;
+       memset(&vmx, 0, sizeof(__vmx_context_t)); 
+       if (__power_vmx())  {
+          ret = ptrace64 (PTT_READ_VEC, tid, (long long) &vmx, 0, 0);
+          if (ret < 0)
+          {
+             if (errno == ENXIO) {
+               warning (_("Unable to fetch AltiVec registers."));
+               return;
+             }
+          }  
+          fill_altivec(regcache, &vmx);
+          ret = ptrace64 (PTT_WRITE_VEC, tid, (long long) &vmx, 0, 0);
+          if (ret < 0)
+             perror_with_name (_("Unable to store AltiVec register."));
+       }
+    }
+    /* vmx registers */
+    if (tdep->ppc_vsr0_upper_regnum != -1 && regno >= tdep->ppc_vsr0_upper_regnum) {
+       __vsx_context_t vsx;
+       memset(&vsx, 0, sizeof(__vsx_context_t)); 
+       if (__power_vsx())  {
+           int i = 0, ret = 0;
+           ret = ptrace64 (PTT_READ_VSX, tid, (long long) &vsx, 0, 0);
+           if (ret < 0)
+           {
+             if (errno == ENXIO) {
+               warning (_("Unable to fetch VSX registers."));
+               return;
+             }
+           }
+           fill_vsx (regcache, &vsx);
+           ret = ptrace64 (PTT_WRITE_VSX, tid, (long long) &vsx, 0, 0);
+           if (ret < 0)
+              perror_with_name (_("Unable to store VSX register."));
+
+       }
+    }
 }
 
 /* Store gdb's current view of the register set into the
--- ./gdb/rs6000-aix-tdep.c_orig	2017-02-05 21:55:41 -0600
+++ ./gdb/rs6000-aix-tdep.c	2017-02-04 08:38:50 -0600
@@ -72,9 +72,9 @@
   4,  /* fpscr_size */
 
   /* AltiVec registers.  */
-  -1, /* vr0_offset */
-  -1, /* vscr_offset */
-  -1 /* vrsave_offset */
+  32, /* vr0_offset */
+  544, /* vscr_offset. */
+  560 /* vrsave_offset */
 };
 
 static struct ppc_reg_offsets rs6000_aix64_reg_offsets =
@@ -102,6 +102,18 @@
   -1 /* vrsave_offset */
 };
 
+static const struct regset ppc32_aix_vrregset = {
+  &rs6000_aix32_reg_offsets,
+  ppc_supply_vrregset,
+  ppc_collect_vrregset
+};
+
+static const struct regset ppc32_aix_vsxregset = {
+  &rs6000_aix32_reg_offsets,
+  ppc_supply_vsxregset,
+  ppc_collect_vsxregset
+};
+
 
 /* Supply register REGNUM in the general-purpose register set REGSET
    from the buffer specified by GREGS and LEN to register cache
@@ -154,10 +166,21 @@
 					 void *cb_data,
 					 const struct regcache *regcache)
 {
+  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
+  int have_altivec = tdep->ppc_vr0_regnum != -1;
+  int have_vsx = tdep->ppc_vsr0_upper_regnum != -1;
+
   if (gdbarch_tdep (gdbarch)->wordsize == 4)
     cb (".reg", 592, &rs6000_aix32_regset, NULL, cb_data);
   else
     cb (".reg", 576, &rs6000_aix64_regset, NULL, cb_data);
+
+  if (have_altivec)
+    cb (".aix-vmx", 560, &ppc32_aix_vrregset, "AIX altivec", cb_data); 
+
+  if (have_vsx)
+    cb (".aix-vsx", 256, &ppc32_aix_vsxregset, "AIX vsx", cb_data);
+
 }
 
 
--- ./bfd/aix5ppc-core.c_orig	2017-02-05 21:56:12 -0600
+++ ./bfd/aix5ppc-core.c	2017-02-04 08:38:50 -0600
@@ -143,6 +143,29 @@
   sec->filepos = 0;
   sec->contents = (bfd_byte *)&new_core_hdr->c_flt.r64;
 
+  if (core.c_extctx) 
+  {
+      /* .vmx section. */
+      flags = SEC_HAS_CONTENTS;
+      sec = bfd_make_section_anyway_with_flags (abfd, ".aix-vmx", flags);
+      if (NULL == sec)
+        return return_value;
+
+      sec->size = 560;
+      sec->vma = 0;
+      sec->filepos = core.c_extctx;
+
+      /* .vsx section. */
+      flags = SEC_HAS_CONTENTS;
+      sec = bfd_make_section_anyway_with_flags (abfd, ".aix-vsx", flags);
+      if (NULL == sec)
+        return return_value;
+
+      sec->size = 256;
+      sec->vma = 0;
+      sec->filepos = core.c_extctx + 584;
+  }
+
   /* .ldinfo section.
      To actually find out how long this section is in this particular
      core dump would require going down the whole list of struct
--- ./bfd/rs6000-core.c_orig	2017-02-05 21:56:47 -0600
+++ ./bfd/rs6000-core.c	2017-02-04 08:38:50 -0600
@@ -342,7 +342,7 @@
   /* Values from new and old core structures.  */
   int c_flag;
   file_ptr c_stack, c_regoff, c_loader;
-  bfd_size_type c_size, c_regsize, c_lsize;
+  bfd_size_type c_size, c_regsize, c_lsize, c_extoff;
   bfd_vma c_stackend;
   void *c_regptr;
   int proc64;
@@ -370,6 +370,7 @@
       c_stackend = CNEW_STACKORG (core.new_dump) + c_size;
       c_lsize = CNEW_LSIZE (core.new_dump);
       c_loader = CNEW_LOADER (core.new_dump);
+      c_extoff = core.new_dump.c_extctx;
   #ifndef BFD64
       proc64 = CNEW_PROC64 (core.new_dump);
     }
@@ -516,6 +517,19 @@
 			  c_regsize, (bfd_vma) 0, c_regoff))
     goto fail;
 
+  if (c_extoff)
+  {
+      if (!make_bfd_asection (abfd, ".aix-vmx",
+                              SEC_HAS_CONTENTS,
+                              560, (bfd_vma) 0, c_extoff))
+        goto fail;
+
+      if (!make_bfd_asection (abfd, ".aix-vsx",
+                             SEC_HAS_CONTENTS,
+                              256, (bfd_vma) 0, c_extoff + 584))
+        goto fail;
+  }
+
   /* .ldinfo section.
      To actually find out how long this section is in this particular
      core dump would require going down the whole list of struct ld_info's.
