diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 9d316fbce98..5bf169ca02d 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -1,3 +1,23 @@
+2018-06-05  Andrew Burgess  <andrew.burgess@embecosm.com>
+
+	* arm-tdep.c (arm_unwind_pc): Delete.
+	(arm_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+	* frame-unwind.c (default_unwind_pc): Rewrite to call
+	extract_typed_address and gdbarch_addr_bits_remove.
+	* i386-tdep.c (i386_unwind_pc): Delete.
+	(i386_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+	* m68k-tdep.c (m68k_unwind_pc): Delete.
+	(m68k_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+	* nios2-tdep.c (nios2_unwind_pc): Delete.
+	(nios2_get_next_pc): Update to call gdbarch_unwind_pc.
+	(nios2_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+	* rl78-tdep.c (rl78_unwind_pc): Delete.
+	(rl78_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+	* s390-tdep.c (s390_unwind_pc): Delete.
+	(s390_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+	* tic6x-tdep.c (tic6x_unwind_pc): Delete.
+	(tic6x_gdbarch_init): Delete use of set_gdbarch_unwind_pc.
+
 2018-06-05  Andrew Burgess  <andrew.burgess@embecosm.com>
 
 	* aarch64-tdep.c (aarch64_unwind_pc): Deleted.
diff --git a/gdb/arm-tdep.c b/gdb/arm-tdep.c
index 3ea0e79b739..45c5b36383a 100644
--- a/gdb/arm-tdep.c
+++ b/gdb/arm-tdep.c
@@ -3069,18 +3069,6 @@ arm_dummy_id (struct gdbarch *gdbarch, struct frame_info *this_frame)
 			 get_frame_pc (this_frame));
 }
 
-/* Given THIS_FRAME, find the previous frame's resume PC (which will
-   be used to construct the previous frame's ID, after looking up the
-   containing function).  */
-
-static CORE_ADDR
-arm_unwind_pc (struct gdbarch *gdbarch, struct frame_info *this_frame)
-{
-  CORE_ADDR pc;
-  pc = frame_unwind_register_unsigned (this_frame, ARM_PC_REGNUM);
-  return arm_addr_bits_remove (gdbarch, pc);
-}
-
 static CORE_ADDR
 arm_unwind_sp (struct gdbarch *gdbarch, struct frame_info *this_frame)
 {
@@ -9360,7 +9348,6 @@ arm_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
 
   /* Frame handling.  */
   set_gdbarch_dummy_id (gdbarch, arm_dummy_id);
-  set_gdbarch_unwind_pc (gdbarch, arm_unwind_pc);
   set_gdbarch_unwind_sp (gdbarch, arm_unwind_sp);
 
   frame_base_set_default (gdbarch, &arm_normal_base);
diff --git a/gdb/frame-unwind.c b/gdb/frame-unwind.c
index 0eed572ebbb..d5b20e4af73 100644
--- a/gdb/frame-unwind.c
+++ b/gdb/frame-unwind.c
@@ -198,8 +198,19 @@ default_frame_unwind_stop_reason (struct frame_info *this_frame,
 CORE_ADDR
 default_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
 {
-  int pc_regnum = gdbarch_pc_regnum (gdbarch);
-  return frame_unwind_register_unsigned (next_frame, pc_regnum);
+  struct type *type;
+  int pc_regnum;
+  CORE_ADDR addr;
+  struct value *value;
+
+  pc_regnum = gdbarch_pc_regnum (gdbarch);
+  value = frame_unwind_register_value (next_frame, pc_regnum);
+  type = builtin_type (gdbarch)->builtin_func_ptr;
+  addr = extract_typed_address (value_contents_all (value), type);
+  addr = gdbarch_addr_bits_remove (gdbarch, addr);
+
+  release_value (value);
+  return addr;
 }
 
 /* Helper functions for value-based register unwinding.  These return
diff --git a/gdb/i386-tdep.c b/gdb/i386-tdep.c
index b1d502f4827..8f443734a35 100644
--- a/gdb/i386-tdep.c
+++ b/gdb/i386-tdep.c
@@ -1955,17 +1955,6 @@ i386_skip_main_prologue (struct gdbarch *gdbarch, CORE_ADDR pc)
 
   return pc;
 }
-
-/* This function is 64-bit safe.  */
-
-static CORE_ADDR
-i386_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
-{
-  gdb_byte buf[8];
-
-  frame_unwind_register (next_frame, gdbarch_pc_regnum (gdbarch), buf);
-  return extract_typed_address (buf, builtin_type (gdbarch)->builtin_func_ptr);
-}
 
 
 /* Normal frames.  */
@@ -8501,8 +8490,6 @@ i386_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
 
   set_gdbarch_dummy_id (gdbarch, i386_dummy_id);
 
-  set_gdbarch_unwind_pc (gdbarch, i386_unwind_pc);
-
   /* Add the i386 register groups.  */
   i386_add_reggroups (gdbarch);
   tdep->register_reggroup_p = i386_register_reggroup_p;
diff --git a/gdb/m68k-tdep.c b/gdb/m68k-tdep.c
index a6e9b58a7d1..8d33bc2f661 100644
--- a/gdb/m68k-tdep.c
+++ b/gdb/m68k-tdep.c
@@ -850,15 +850,6 @@ m68k_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR start_pc)
     return start_pc;
   return pc;
 }
-
-static CORE_ADDR
-m68k_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
-{
-  gdb_byte buf[8];
-
-  frame_unwind_register (next_frame, gdbarch_pc_regnum (gdbarch), buf);
-  return extract_typed_address (buf, builtin_type (gdbarch)->builtin_func_ptr);
-}
 
 /* Normal frames.  */
 
@@ -1246,7 +1237,6 @@ m68k_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
 
   /* Frame unwinder.  */
   set_gdbarch_dummy_id (gdbarch, m68k_dummy_id);
-  set_gdbarch_unwind_pc (gdbarch, m68k_unwind_pc);
 
   /* Hook in the DWARF CFI frame unwinder.  */
   dwarf2_append_unwinders (gdbarch);
diff --git a/gdb/nios2-tdep.c b/gdb/nios2-tdep.c
index 91b4381f0b7..b6533d57719 100644
--- a/gdb/nios2-tdep.c
+++ b/gdb/nios2-tdep.c
@@ -1888,17 +1888,6 @@ nios2_push_dummy_call (struct gdbarch *gdbarch, struct value *function,
   return sp;
 }
 
-/* Implement the unwind_pc gdbarch method.  */
-
-static CORE_ADDR
-nios2_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
-{
-  gdb_byte buf[4];
-
-  frame_unwind_register (next_frame, NIOS2_PC_REGNUM, buf);
-  return extract_typed_address (buf, builtin_type (gdbarch)->builtin_func_ptr);
-}
-
 /* Implement the unwind_sp gdbarch method.  */
 
 static CORE_ADDR
@@ -2186,7 +2175,7 @@ nios2_get_next_pc (struct regcache *regcache, CORE_ADDR pc)
       /* If ra is in the reglist, we have to use the value saved in the
 	 stack frame rather than the current value.  */
       if (uimm & (1 << NIOS2_RA_REGNUM))
-	pc = nios2_unwind_pc (gdbarch, get_current_frame ());
+	pc = gdbarch_unwind_pc (gdbarch, get_current_frame ());
       else
 	pc = regcache_raw_get_unsigned (regcache, NIOS2_RA_REGNUM);
     }
@@ -2322,7 +2311,6 @@ nios2_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
   set_gdbarch_sw_breakpoint_from_kind (gdbarch, nios2_sw_breakpoint_from_kind);
 
   set_gdbarch_dummy_id (gdbarch, nios2_dummy_id);
-  set_gdbarch_unwind_pc (gdbarch, nios2_unwind_pc);
   set_gdbarch_unwind_sp (gdbarch, nios2_unwind_sp);
 
   /* The dwarf2 unwinder will normally produce the best results if
diff --git a/gdb/rl78-tdep.c b/gdb/rl78-tdep.c
index ace01b1171a..70955d966fa 100644
--- a/gdb/rl78-tdep.c
+++ b/gdb/rl78-tdep.c
@@ -1074,16 +1074,6 @@ rl78_skip_prologue (struct gdbarch *gdbarch, CORE_ADDR pc)
   return p.prologue_end;
 }
 
-/* Implement the "unwind_pc" gdbarch method.  */
-
-static CORE_ADDR
-rl78_unwind_pc (struct gdbarch *arch, struct frame_info *next_frame)
-{
-  return rl78_addr_bits_remove
-           (arch, frame_unwind_register_unsigned (next_frame,
-	                                          RL78_PC_REGNUM));
-}
-
 /* Implement the "unwind_sp" gdbarch method.  */
 
 static CORE_ADDR
@@ -1468,7 +1458,6 @@ rl78_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
   /* Frames, prologues, etc.  */
   set_gdbarch_inner_than (gdbarch, core_addr_lessthan);
   set_gdbarch_skip_prologue (gdbarch, rl78_skip_prologue);
-  set_gdbarch_unwind_pc (gdbarch, rl78_unwind_pc);
   set_gdbarch_unwind_sp (gdbarch, rl78_unwind_sp);
   set_gdbarch_frame_align (gdbarch, rl78_frame_align);
 
diff --git a/gdb/s390-tdep.c b/gdb/s390-tdep.c
index e4e08c706a1..f6b29380d10 100644
--- a/gdb/s390-tdep.c
+++ b/gdb/s390-tdep.c
@@ -2118,17 +2118,6 @@ s390_stack_frame_destroyed_p (struct gdbarch *gdbarch, CORE_ADDR pc)
   return 0;
 }
 
-/* Implement unwind_pc gdbarch method.  */
-
-static CORE_ADDR
-s390_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
-{
-  struct gdbarch_tdep *tdep = gdbarch_tdep (gdbarch);
-  ULONGEST pc;
-  pc = frame_unwind_register_unsigned (next_frame, tdep->pc_regnum);
-  return gdbarch_addr_bits_remove (gdbarch, pc);
-}
-
 /* Implement unwind_sp gdbarch method.  */
 
 static CORE_ADDR
@@ -6996,7 +6985,6 @@ s390_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
   dwarf2_frame_set_init_reg (gdbarch, s390_dwarf2_frame_init_reg);
   dwarf2_frame_set_adjust_regnum (gdbarch, s390_adjust_frame_regnum);
   dwarf2_append_unwinders (gdbarch);
-  set_gdbarch_unwind_pc (gdbarch, s390_unwind_pc);
   set_gdbarch_unwind_sp (gdbarch, s390_unwind_sp);
 
   switch (info.bfd_arch_info->mach)
diff --git a/gdb/tic6x-tdep.c b/gdb/tic6x-tdep.c
index efb8b0561b4..1d2671f155f 100644
--- a/gdb/tic6x-tdep.c
+++ b/gdb/tic6x-tdep.c
@@ -366,17 +366,6 @@ tic6x_dwarf2_frame_init_reg (struct gdbarch *gdbarch, int regnum,
     reg->how = DWARF2_FRAME_REG_UNDEFINED;
 }
 
-/* This is the implementation of gdbarch method unwind_pc.  */
-
-static CORE_ADDR
-tic6x_unwind_pc (struct gdbarch *gdbarch, struct frame_info *next_frame)
-{
-  gdb_byte buf[8];
-
-  frame_unwind_register (next_frame,  TIC6X_PC_REGNUM, buf);
-  return extract_typed_address (buf, builtin_type (gdbarch)->builtin_func_ptr);
-}
-
 /* This is the implementation of gdbarch method unwind_sp.  */
 
 static CORE_ADDR
@@ -1284,7 +1273,6 @@ tic6x_gdbarch_init (struct gdbarch_info info, struct gdbarch_list *arches)
   set_gdbarch_sw_breakpoint_from_kind (gdbarch,
 				       tic6x_sw_breakpoint_from_kind);
 
-  set_gdbarch_unwind_pc (gdbarch, tic6x_unwind_pc);
   set_gdbarch_unwind_sp (gdbarch, tic6x_unwind_sp);
 
   /* Unwinding.  */
