[v6,7/7] adapt btrace testcases for arm target

Message ID 20210531213307.275079-8-zied.guermazi@trande.de
State New
Headers show
Series
  • extend branch tracing to use ARM CoreSight traces
Related show

Commit Message

Zied Guermazi May 31, 2021, 9:33 p.m.
This patch extends the test suite for btrace to cover using
ARM CoreSight traces.

gdb/ChangeLog
	* testsuite/lib/gdb.exp (skip_btrace_tests): enable btrace tests
	for arm.
	* testsuite/gdb.btrace/buffer-size.exp: enable btrace tests
	and adapt test for arm.
	* testsuite/gdb.btrace/delta.exp (check_trace): enable btrace tests
	and adapt test for arm.
	* testsuite/gdb.btrace/instruction_history.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/instruction_history.S: renamed to
	x86-instruction_history.S.
	* testsuite/gdb.btrace/aarch64-instruction_history.S: New.
	* testsuite/gdb.btrace/arm-instruction_history.S: New.
	* testsuite/gdb.btrace/non-stop.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/reconnect.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/record_goto.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/aarch64-record_goto.S: New.
	* testsuite/gdb.btrace/arm-record_goto.S: New.
	* testsuite/gdb.btrace/stepi.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/tailcall.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/aarch64-tailcall.S: New.
	* testsuite/gdb.btrace/arm-tailcall.S: New.
	* testsuite/gdb.btrace/tailcall-only.exp: enable btrace tests
	and adapt tests for arm.
	* testsuite/gdb.btrace/aarch64-tailcall-only.S: New.
	* testsuite/gdb.btrace/arm-tailcall-only.S: New.
---
 .../gdb.btrace/aarch64-instruction_history.S  |  31 ++
 .../gdb.btrace/aarch64-record_goto.S          | 399 ++++++++++++++
 .../gdb.btrace/aarch64-tailcall-only.S        | 516 ++++++++++++++++++
 gdb/testsuite/gdb.btrace/aarch64-tailcall.S   | 408 ++++++++++++++
 .../gdb.btrace/arm-instruction_history.S      |  31 ++
 gdb/testsuite/gdb.btrace/arm-record_goto.S    | 432 +++++++++++++++
 gdb/testsuite/gdb.btrace/arm-tailcall-only.S  | 503 +++++++++++++++++
 gdb/testsuite/gdb.btrace/arm-tailcall.S       | 390 +++++++++++++
 gdb/testsuite/gdb.btrace/buffer-size.exp      |  15 +-
 .../gdb.btrace/instruction_history.exp        | 106 +++-
 gdb/testsuite/gdb.btrace/non-stop.exp         |  60 +-
 gdb/testsuite/gdb.btrace/record_goto.exp      | 253 ++++++---
 gdb/testsuite/gdb.btrace/stepi.exp            | 107 +++-
 gdb/testsuite/gdb.btrace/tailcall-only.exp    |  20 +-
 gdb/testsuite/gdb.btrace/tailcall.exp         |  58 +-
 ...on_history.S => x86-instruction_history.S} |   0
 gdb/testsuite/lib/gdb.exp                     |   2 +-
 17 files changed, 3189 insertions(+), 142 deletions(-)
 create mode 100644 gdb/testsuite/gdb.btrace/aarch64-instruction_history.S
 create mode 100644 gdb/testsuite/gdb.btrace/aarch64-record_goto.S
 create mode 100644 gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S
 create mode 100644 gdb/testsuite/gdb.btrace/aarch64-tailcall.S
 create mode 100644 gdb/testsuite/gdb.btrace/arm-instruction_history.S
 create mode 100644 gdb/testsuite/gdb.btrace/arm-record_goto.S
 create mode 100644 gdb/testsuite/gdb.btrace/arm-tailcall-only.S
 create mode 100644 gdb/testsuite/gdb.btrace/arm-tailcall.S
 rename gdb/testsuite/gdb.btrace/{instruction_history.S => x86-instruction_history.S} (100%)

-- 
2.25.1

Comments

Weimin Pan via Gdb-patches June 22, 2021, 9:28 p.m. | #1
On Mon, May 31, 2021 at 11:33:07PM +0200, Zied Guermazi wrote:
> This patch extends the test suite for btrace to cover using

> ARM CoreSight traces.

> 

> gdb/ChangeLog

> 	* testsuite/lib/gdb.exp (skip_btrace_tests): enable btrace tests

> 	for arm.

> 	* testsuite/gdb.btrace/buffer-size.exp: enable btrace tests

> 	and adapt test for arm.

> 	* testsuite/gdb.btrace/delta.exp (check_trace): enable btrace tests

> 	and adapt test for arm.

> 	* testsuite/gdb.btrace/instruction_history.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/instruction_history.S: renamed to

> 	x86-instruction_history.S.

> 	* testsuite/gdb.btrace/aarch64-instruction_history.S: New.

> 	* testsuite/gdb.btrace/arm-instruction_history.S: New.

> 	* testsuite/gdb.btrace/non-stop.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/reconnect.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/record_goto.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/aarch64-record_goto.S: New.

> 	* testsuite/gdb.btrace/arm-record_goto.S: New.

> 	* testsuite/gdb.btrace/stepi.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/tailcall.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/aarch64-tailcall.S: New.

> 	* testsuite/gdb.btrace/arm-tailcall.S: New.

> 	* testsuite/gdb.btrace/tailcall-only.exp: enable btrace tests

> 	and adapt tests for arm.

> 	* testsuite/gdb.btrace/aarch64-tailcall-only.S: New.

> 	* testsuite/gdb.btrace/arm-tailcall-only.S: New.


Hi,

I only skimmed through and do not have much to say about the content of the
patch itself, but I guess this should go in gdb/testsuite/ChangeLog, not
in gdb/ChangeLog.

Best
Lancelot.

> ---

>  .../gdb.btrace/aarch64-instruction_history.S  |  31 ++

>  .../gdb.btrace/aarch64-record_goto.S          | 399 ++++++++++++++

>  .../gdb.btrace/aarch64-tailcall-only.S        | 516 ++++++++++++++++++

>  gdb/testsuite/gdb.btrace/aarch64-tailcall.S   | 408 ++++++++++++++

>  .../gdb.btrace/arm-instruction_history.S      |  31 ++

>  gdb/testsuite/gdb.btrace/arm-record_goto.S    | 432 +++++++++++++++

>  gdb/testsuite/gdb.btrace/arm-tailcall-only.S  | 503 +++++++++++++++++

>  gdb/testsuite/gdb.btrace/arm-tailcall.S       | 390 +++++++++++++

>  gdb/testsuite/gdb.btrace/buffer-size.exp      |  15 +-

>  .../gdb.btrace/instruction_history.exp        | 106 +++-

>  gdb/testsuite/gdb.btrace/non-stop.exp         |  60 +-

>  gdb/testsuite/gdb.btrace/record_goto.exp      | 253 ++++++---

>  gdb/testsuite/gdb.btrace/stepi.exp            | 107 +++-

>  gdb/testsuite/gdb.btrace/tailcall-only.exp    |  20 +-

>  gdb/testsuite/gdb.btrace/tailcall.exp         |  58 +-

>  ...on_history.S => x86-instruction_history.S} |   0

>  gdb/testsuite/lib/gdb.exp                     |   2 +-

>  17 files changed, 3189 insertions(+), 142 deletions(-)

>  create mode 100644 gdb/testsuite/gdb.btrace/aarch64-instruction_history.S

>  create mode 100644 gdb/testsuite/gdb.btrace/aarch64-record_goto.S

>  create mode 100644 gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S

>  create mode 100644 gdb/testsuite/gdb.btrace/aarch64-tailcall.S

>  create mode 100644 gdb/testsuite/gdb.btrace/arm-instruction_history.S

>  create mode 100644 gdb/testsuite/gdb.btrace/arm-record_goto.S

>  create mode 100644 gdb/testsuite/gdb.btrace/arm-tailcall-only.S

>  create mode 100644 gdb/testsuite/gdb.btrace/arm-tailcall.S

>  rename gdb/testsuite/gdb.btrace/{instruction_history.S => x86-instruction_history.S} (100%)

> 

> diff --git a/gdb/testsuite/gdb.btrace/aarch64-instruction_history.S b/gdb/testsuite/gdb.btrace/aarch64-instruction_history.S

> new file mode 100644

> index 00000000000..0ccf43a1cf4

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/aarch64-instruction_history.S

> @@ -0,0 +1,31 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.  */

> +.arch armv8-a

> +.text

> +.globl loop

> +.type  loop, %function

> +loop:

> +	mov x0, #2 /* bp.1 */

> +L1:

> +	cmp x0, #0

> +	beq L2

> +	subs x0, x0, #1

> +	b L1

> +L2:

> +	ret /* bp.2 */

> +

> +

> diff --git a/gdb/testsuite/gdb.btrace/aarch64-record_goto.S b/gdb/testsuite/gdb.btrace/aarch64-record_goto.S

> new file mode 100644

> index 00000000000..282f8d41a3c

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/aarch64-record_goto.S

> @@ -0,0 +1,399 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.

> +

> +   This file has been generated on an armv8 machine using:

> +   gcc -S -dA -g record_goto.c -o aarch64-record_goto.S  */

> +

> +	.arch armv8-a

> +	.file	"record_goto.c"

> +	.text

> +.Ltext0:

> +	.align	2

> +	.global	fun1

> +	//.tune generic

> +	.type	fun1, %function

> +fun1:

> +.LFB0:

> +	.file 1 "record_goto.c"

> +	// record_goto.c:22:1

> +	.loc 1 22 1

> +	.cfi_startproc

> +// BLOCK 2 seq:0

> +// PRED: ENTRY (FALLTHRU)

> +	// record_goto.c:23:1

> +	.loc 1 23 1

> +	nop

> +// SUCC: EXIT [always] 

> +	ret

> +	.cfi_endproc

> +.LFE0:

> +	.size	fun1, .-fun1

> +	.align	2

> +	.global	fun2

> +	.type	fun2, %function

> +fun2:

> +.LFB1:

> +	// record_goto.c:27:1

> +	.loc 1 27 1

> +	.cfi_startproc

> +// BLOCK 2 seq:0

> +// PRED: ENTRY (FALLTHRU)

> +	stp	x29, x30, [sp, -16]!

> +	.cfi_def_cfa_offset 16

> +	.cfi_offset 29, -16

> +	.cfi_offset 30, -8

> +	mov	x29, sp

> +	// record_goto.c:28:3

> +	.loc 1 28 3

> +	bl	fun1

> +	// record_goto.c:29:1

> +	.loc 1 29 1

> +	nop

> +	ldp	x29, x30, [sp], 16

> +	.cfi_restore 30

> +	.cfi_restore 29

> +	.cfi_def_cfa_offset 0

> +// SUCC: EXIT [always] 

> +	ret

> +	.cfi_endproc

> +.LFE1:

> +	.size	fun2, .-fun2

> +	.align	2

> +	.global	fun3

> +	.type	fun3, %function

> +fun3:

> +.LFB2:

> +	// record_goto.c:33:1

> +	.loc 1 33 1

> +	.cfi_startproc

> +// BLOCK 2 seq:0

> +// PRED: ENTRY (FALLTHRU)

> +	stp	x29, x30, [sp, -16]!

> +	.cfi_def_cfa_offset 16

> +	.cfi_offset 29, -16

> +	.cfi_offset 30, -8

> +	mov	x29, sp

> +	// record_goto.c:34:3

> +	.loc 1 34 3

> +	bl	fun1

> +	// record_goto.c:35:3

> +	.loc 1 35 3

> +	bl	fun2

> +	// record_goto.c:36:1

> +	.loc 1 36 1

> +	nop

> +	ldp	x29, x30, [sp], 16

> +	.cfi_restore 30

> +	.cfi_restore 29

> +	.cfi_def_cfa_offset 0

> +// SUCC: EXIT [always] 

> +	ret

> +	.cfi_endproc

> +.LFE2:

> +	.size	fun3, .-fun3

> +	.align	2

> +	.global	fun4

> +	.type	fun4, %function

> +fun4:

> +.LFB3:

> +	// record_goto.c:40:1

> +	.loc 1 40 1

> +	.cfi_startproc

> +// BLOCK 2 seq:0

> +// PRED: ENTRY (FALLTHRU)

> +	stp	x29, x30, [sp, -16]!

> +	.cfi_def_cfa_offset 16

> +	.cfi_offset 29, -16

> +	.cfi_offset 30, -8

> +	mov	x29, sp

> +	// record_goto.c:41:3

> +	.loc 1 41 3

> +	bl	fun1

> +	// record_goto.c:42:3

> +	.loc 1 42 3

> +	bl	fun2

> +	// record_goto.c:43:3

> +	.loc 1 43 3

> +	bl	fun3

> +	// record_goto.c:44:1

> +	.loc 1 44 1

> +	nop

> +	ldp	x29, x30, [sp], 16

> +	.cfi_restore 30

> +	.cfi_restore 29

> +	.cfi_def_cfa_offset 0

> +// SUCC: EXIT [always] 

> +	ret

> +	.cfi_endproc

> +.LFE3:

> +	.size	fun4, .-fun4

> +	.align	2

> +	.global	main

> +	.type	main, %function

> +main:

> +.LFB4:

> +	// record_goto.c:48:1

> +	.loc 1 48 1

> +	.cfi_startproc

> +// BLOCK 2 seq:0

> +// PRED: ENTRY (FALLTHRU)

> +	stp	x29, x30, [sp, -16]!

> +	.cfi_def_cfa_offset 16

> +	.cfi_offset 29, -16

> +	.cfi_offset 30, -8

> +	mov	x29, sp

> +	// record_goto.c:49:3

> +	.loc 1 49 3

> +	bl	fun4

> +	// record_goto.c:50:10

> +	.loc 1 50 10

> +	mov	w0, 0

> +	// record_goto.c:51:1

> +	.loc 1 51 1

> +	ldp	x29, x30, [sp], 16

> +	.cfi_restore 30

> +	.cfi_restore 29

> +	.cfi_def_cfa_offset 0

> +// SUCC: EXIT [always] 

> +	ret

> +	.cfi_endproc

> +.LFE4:

> +	.size	main, .-main

> +.Letext0:

> +	.section	.debug_info,"",@progbits

> +.Ldebug_info0:

> +	.4byte	0xb7	// Length of Compilation Unit Info

> +	.2byte	0x4	// DWARF version number

> +	.4byte	.Ldebug_abbrev0	// Offset Into Abbrev. Section

> +	.byte	0x8	// Pointer Size (in bytes)

> +	.uleb128 0x1	// (DIE (0xb) DW_TAG_compile_unit)

> +	.4byte	.LASF4	// DW_AT_producer: "GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -fasynchronous-unwind-tables"

> +	.byte	0xc	// DW_AT_language

> +	.4byte	.LASF5	// DW_AT_name: "record_goto.c"

> +	.4byte	.LASF6	// DW_AT_comp_dir: "/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +	.8byte	.Ltext0	// DW_AT_low_pc

> +	.8byte	.Letext0-.Ltext0	// DW_AT_high_pc

> +	.4byte	.Ldebug_line0	// DW_AT_stmt_list

> +	.uleb128 0x2	// (DIE (0x2d) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF7	// DW_AT_name: "main"

> +	.byte	0x1	// DW_AT_decl_file (record_goto.c)

> +	.byte	0x2f	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x4b	// DW_AT_type

> +	.8byte	.LFB4	// DW_AT_low_pc

> +	.8byte	.LFE4-.LFB4	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x3	// (DIE (0x4b) DW_TAG_base_type)

> +	.byte	0x4	// DW_AT_byte_size

> +	.byte	0x5	// DW_AT_encoding

> +	.ascii "int\0"	// DW_AT_name

> +	.uleb128 0x4	// (DIE (0x52) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF0	// DW_AT_name: "fun4"

> +	.byte	0x1	// DW_AT_decl_file (record_goto.c)

> +	.byte	0x27	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.8byte	.LFB3	// DW_AT_low_pc

> +	.8byte	.LFE3-.LFB3	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x4	// (DIE (0x6c) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF1	// DW_AT_name: "fun3"

> +	.byte	0x1	// DW_AT_decl_file (record_goto.c)

> +	.byte	0x20	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.8byte	.LFB2	// DW_AT_low_pc

> +	.8byte	.LFE2-.LFB2	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x4	// (DIE (0x86) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF2	// DW_AT_name: "fun2"

> +	.byte	0x1	// DW_AT_decl_file (record_goto.c)

> +	.byte	0x1a	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.8byte	.LFB1	// DW_AT_low_pc

> +	.8byte	.LFE1-.LFB1	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x5	// (DIE (0xa0) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF3	// DW_AT_name: "fun1"

> +	.byte	0x1	// DW_AT_decl_file (record_goto.c)

> +	.byte	0x15	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.8byte	.LFB0	// DW_AT_low_pc

> +	.8byte	.LFE0-.LFB0	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.byte	0	// end of children of DIE 0xb

> +	.section	.debug_abbrev,"",@progbits

> +.Ldebug_abbrev0:

> +	.uleb128 0x1	// (abbrev code)

> +	.uleb128 0x11	// (TAG: DW_TAG_compile_unit)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x25	// (DW_AT_producer)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x13	// (DW_AT_language)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x1b	// (DW_AT_comp_dir)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x10	// (DW_AT_stmt_list)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x2	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3f	// (DW_AT_external)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2116	// (DW_AT_GNU_all_tail_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x3	// (abbrev code)

> +	.uleb128 0x24	// (TAG: DW_TAG_base_type)

> +	.byte	0	// DW_children_no

> +	.uleb128 0xb	// (DW_AT_byte_size)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3e	// (DW_AT_encoding)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0x8	// (DW_FORM_string)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x4	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3f	// (DW_AT_external)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2116	// (DW_AT_GNU_all_tail_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x5	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3f	// (DW_AT_external)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.byte	0

> +	.section	.debug_aranges,"",@progbits

> +	.4byte	0x2c	// Length of Address Ranges Info

> +	.2byte	0x2	// DWARF aranges version

> +	.4byte	.Ldebug_info0	// Offset of Compilation Unit Info

> +	.byte	0x8	// Size of Address

> +	.byte	0	// Size of Segment Descriptor

> +	.2byte	0	// Pad to 16 byte boundary

> +	.2byte	0

> +	.8byte	.Ltext0	// Address

> +	.8byte	.Letext0-.Ltext0	// Length

> +	.8byte	0

> +	.8byte	0

> +	.section	.debug_line,"",@progbits

> +.Ldebug_line0:

> +	.section	.debug_str,"MS",@progbits,1

> +.LASF5:

> +	.string	"record_goto.c"

> +.LASF4:

> +	.string	"GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -fasynchronous-unwind-tables"

> +.LASF3:

> +	.string	"fun1"

> +.LASF2:

> +	.string	"fun2"

> +.LASF0:

> +	.string	"fun4"

> +.LASF6:

> +	.string	"/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +.LASF7:

> +	.string	"main"

> +.LASF1:

> +	.string	"fun3"

> +	.ident	"GCC: (Debian 10.2.1-3) 10.2.1 20201224"

> +	.section	.note.GNU-stack,"",@progbits

> diff --git a/gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S b/gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S

> new file mode 100644

> index 00000000000..f3e12ef2bc8

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S

> @@ -0,0 +1,516 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.

> +

> +   This file has been generated on an armv8 machine using:

> +   gcc -m32 -S -O2 -dA -g tailcall-only.c -o aarch64-tailcall-only.S

> + */

> +

> +	.arch armv8-a

> +	.file	"tailcall-only.c"

> +	.text

> +.Ltext0:

> +	.align	2

> +	.p2align 4,,11

> +	//.tune generic

> +	.type	bar_1, %function

> +bar_1:

> +.LFB0:

> +	.file 1 "tailcall-only.c"

> +	// tailcall-only.c:22:1

> +	.loc 1 22 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall-only.c:23:3

> +	.loc 1 23 3 view .LVU1

> +	// tailcall-only.c:24:1

> +	.loc 1 24 1 is_stmt 0 view .LVU2

> +	mov	w0, 42

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally)

> +	ret

> +	.cfi_endproc

> +.LFE0:

> +	.size	bar_1, .-bar_1

> +	.align	2

> +	.p2align 4,,11

> +	.type	bar, %function

> +bar:

> +.LFB1:

> +	// tailcall-only.c:28:1

> +	.loc 1 28 1 is_stmt 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall-only.c:29:3

> +	.loc 1 29 3 view .LVU4

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)

> +	// tailcall-only.c:29:10

> +	.loc 1 29 10 is_stmt 0 view .LVU5

> +	b	bar_1

> +.LVL0:

> +	.cfi_endproc

> +.LFE1:

> +	.size	bar, .-bar

> +	.align	2

> +	.p2align 4,,11

> +	.type	foo_1, %function

> +foo_1:

> +.LFB2:

> +	// tailcall-only.c:34:1

> +	.loc 1 34 1 is_stmt 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall-only.c:35:3

> +	.loc 1 35 3 view .LVU7

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)

> +	// tailcall-only.c:35:10

> +	.loc 1 35 10 is_stmt 0 view .LVU8

> +	b	bar

> +.LVL1:

> +	.cfi_endproc

> +.LFE2:

> +	.size	foo_1, .-foo_1

> +	.align	2

> +	.p2align 4,,11

> +	.type	foo, %function

> +foo:

> +.LFB3:

> +	// tailcall-only.c:40:1

> +	.loc 1 40 1 is_stmt 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall-only.c:41:3

> +	.loc 1 41 3 view .LVU10

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)

> +	// tailcall-only.c:41:10

> +	.loc 1 41 10 is_stmt 0 view .LVU11

> +	b	foo_1

> +.LVL2:

> +	.cfi_endproc

> +.LFE3:

> +	.size	foo, .-foo

> +	.section	.text.startup,"ax",@progbits

> +	.align	2

> +	.p2align 4,,11

> +	.global	main

> +	.type	main, %function

> +main:

> +.LFB4:

> +	// tailcall-only.c:46:1

> +	.loc 1 46 1 is_stmt 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall-only.c:47:3

> +	.loc 1 47 3 view .LVU13

> +	// tailcall-only.c:49:3

> +	.loc 1 49 3 view .LVU14

> +	// tailcall-only.c:46:1

> +	.loc 1 46 1 is_stmt 0 view .LVU15

> +	stp	x29, x30, [sp, -16]!

> +	.cfi_def_cfa_offset 16

> +	.cfi_offset 29, -16

> +	.cfi_offset 30, -8

> +	mov	x29, sp

> +	// tailcall-only.c:49:12

> +	.loc 1 49 12 view .LVU16

> +	bl	foo

> +.LVL3:

> +	// DEBUG answer => x0

> +	// tailcall-only.c:50:3

> +	.loc 1 50 3 is_stmt 1 view .LVU17

> +	// DEBUG answer => x0+0x1

> +	// tailcall-only.c:52:3

> +	.loc 1 52 3 view .LVU18

> +	// tailcall-only.c:53:1

> +	.loc 1 53 1 is_stmt 0 view .LVU19

> +	add	w0, w0, 1

> +.LVL4:

> +	// DEBUG answer => x0

> +	// tailcall-only.c:53:1

> +	.loc 1 53 1 view .LVU20

> +	ldp	x29, x30, [sp], 16

> +	.cfi_restore 30

> +	.cfi_restore 29

> +	.cfi_def_cfa_offset 0

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally)

> +	ret

> +	.cfi_endproc

> +.LFE4:

> +	.size	main, .-main

> +	.text

> +.Letext0:

> +	.section	.debug_info,"",@progbits

> +.Ldebug_info0:

> +	.4byte	0x11f	// Length of Compilation Unit Info

> +	.2byte	0x4	// DWARF version number

> +	.4byte	.Ldebug_abbrev0	// Offset Into Abbrev. Section

> +	.byte	0x8	// Pointer Size (in bytes)

> +	.uleb128 0x1	// (DIE (0xb) DW_TAG_compile_unit)

> +	.4byte	.LASF1	// DW_AT_producer: "GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"

> +	.byte	0xc	// DW_AT_language

> +	.4byte	.LASF2	// DW_AT_name: "tailcall-only.c"

> +	.4byte	.LASF3	// DW_AT_comp_dir: "/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +	.4byte	.Ldebug_ranges0+0	// DW_AT_ranges

> +	.8byte	0	// DW_AT_low_pc

> +	.4byte	.Ldebug_line0	// DW_AT_stmt_list

> +	.uleb128 0x2	// (DIE (0x29) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF4	// DW_AT_name: "main"

> +	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x2d	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB4	// DW_AT_low_pc

> +	.8byte	.LFE4-.LFB4	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.4byte	0x6d	// DW_AT_sibling

> +	.uleb128 0x3	// (DIE (0x4b) DW_TAG_variable)

> +	.4byte	.LASF5	// DW_AT_name: "answer"

> +	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x2f	// DW_AT_decl_line

> +	.byte	0x7	// DW_AT_decl_column

> +	.4byte	0x6d	// DW_AT_type

> +	.4byte	.LLST0	// DW_AT_location

> +	.4byte	.LVUS0	// DW_AT_GNU_locviews

> +	.uleb128 0x4	// (DIE (0x5f) DW_TAG_GNU_call_site)

> +	.8byte	.LVL3	// DW_AT_low_pc

> +	.4byte	0x74	// DW_AT_abstract_origin

> +	.byte	0	// end of children of DIE 0x29

> +	.uleb128 0x5	// (DIE (0x6d) DW_TAG_base_type)

> +	.byte	0x4	// DW_AT_byte_size

> +	.byte	0x5	// DW_AT_encoding

> +	.ascii "int\0"	// DW_AT_name

> +	.uleb128 0x6	// (DIE (0x74) DW_TAG_subprogram)

> +	.ascii "foo\0"	// DW_AT_name

> +	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x27	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB3	// DW_AT_low_pc

> +	.8byte	.LFE3-.LFB3	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.4byte	0xa4	// DW_AT_sibling

> +	.uleb128 0x7	// (DIE (0x96) DW_TAG_GNU_call_site)

> +	.8byte	.LVL2	// DW_AT_low_pc

> +			// DW_AT_GNU_tail_call

> +	.4byte	0xa4	// DW_AT_abstract_origin

> +	.byte	0	// end of children of DIE 0x74

> +	.uleb128 0x8	// (DIE (0xa4) DW_TAG_subprogram)

> +	.4byte	.LASF0	// DW_AT_name: "foo_1"

> +	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x21	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB2	// DW_AT_low_pc

> +	.8byte	.LFE2-.LFB2	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.4byte	0xd4	// DW_AT_sibling

> +	.uleb128 0x7	// (DIE (0xc6) DW_TAG_GNU_call_site)

> +	.8byte	.LVL1	// DW_AT_low_pc

> +			// DW_AT_GNU_tail_call

> +	.4byte	0xd4	// DW_AT_abstract_origin

> +	.byte	0	// end of children of DIE 0xa4

> +	.uleb128 0x6	// (DIE (0xd4) DW_TAG_subprogram)

> +	.ascii "bar\0"	// DW_AT_name

> +	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x1b	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB1	// DW_AT_low_pc

> +	.8byte	.LFE1-.LFB1	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.4byte	0x104	// DW_AT_sibling

> +	.uleb128 0x7	// (DIE (0xf6) DW_TAG_GNU_call_site)

> +	.8byte	.LVL0	// DW_AT_low_pc

> +			// DW_AT_GNU_tail_call

> +	.4byte	0x104	// DW_AT_abstract_origin

> +	.byte	0	// end of children of DIE 0xd4

> +	.uleb128 0x9	// (DIE (0x104) DW_TAG_subprogram)

> +	.4byte	.LASF6	// DW_AT_name: "bar_1"

> +	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x15	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB0	// DW_AT_low_pc

> +	.8byte	.LFE0-.LFB0	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.byte	0	// end of children of DIE 0xb

> +	.section	.debug_abbrev,"",@progbits

> +.Ldebug_abbrev0:

> +	.uleb128 0x1	// (abbrev code)

> +	.uleb128 0x11	// (TAG: DW_TAG_compile_unit)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x25	// (DW_AT_producer)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x13	// (DW_AT_language)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x1b	// (DW_AT_comp_dir)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x55	// (DW_AT_ranges)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x10	// (DW_AT_stmt_list)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x2	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x3f	// (DW_AT_external)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x1	// (DW_AT_sibling)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x3	// (abbrev code)

> +	.uleb128 0x34	// (TAG: DW_TAG_variable)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x2	// (DW_AT_location)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.uleb128 0x2137	// (DW_AT_GNU_locviews)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x4	// (abbrev code)

> +	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x31	// (DW_AT_abstract_origin)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x5	// (abbrev code)

> +	.uleb128 0x24	// (TAG: DW_TAG_base_type)

> +	.byte	0	// DW_children_no

> +	.uleb128 0xb	// (DW_AT_byte_size)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3e	// (DW_AT_encoding)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0x8	// (DW_FORM_string)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x6	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0x8	// (DW_FORM_string)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x1	// (DW_AT_sibling)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x7	// (abbrev code)

> +	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x2115	// (DW_AT_GNU_tail_call)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x31	// (DW_AT_abstract_origin)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x8	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x1	// (DW_AT_sibling)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x9	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.byte	0

> +	.section	.debug_loc,"",@progbits

> +.Ldebug_loc0:

> +.LVUS0:

> +	.uleb128 .LVU17	// View list begin (*.LVUS0)

> +	.uleb128 .LVU18	// View list end (*.LVUS0)

> +	.uleb128 .LVU18	// View list begin (*.LVUS0)

> +	.uleb128 .LVU20	// View list end (*.LVUS0)

> +	.uleb128 .LVU20	// View list begin (*.LVUS0)

> +	.uleb128 0	// View list end (*.LVUS0)

> +.LLST0:

> +	.8byte	.LVL3	// Location list begin address (*.LLST0)

> +	.8byte	.LVL3	// Location list end address (*.LLST0)

> +	.2byte	0x1	// Location expression size

> +	.byte	0x50	// DW_OP_reg0

> +	.8byte	.LVL3	// Location list begin address (*.LLST0)

> +	.8byte	.LVL4	// Location list end address (*.LLST0)

> +	.2byte	0x3	// Location expression size

> +	.byte	0x70	// DW_OP_breg0

> +	.sleb128 1

> +	.byte	0x9f	// DW_OP_stack_value

> +	.8byte	.LVL4	// Location list begin address (*.LLST0)

> +	.8byte	.LFE4	// Location list end address (*.LLST0)

> +	.2byte	0x1	// Location expression size

> +	.byte	0x50	// DW_OP_reg0

> +	.8byte	0	// Location list terminator begin (*.LLST0)

> +	.8byte	0	// Location list terminator end (*.LLST0)

> +	.section	.debug_aranges,"",@progbits

> +	.4byte	0x3c	// Length of Address Ranges Info

> +	.2byte	0x2	// DWARF aranges version

> +	.4byte	.Ldebug_info0	// Offset of Compilation Unit Info

> +	.byte	0x8	// Size of Address

> +	.byte	0	// Size of Segment Descriptor

> +	.2byte	0	// Pad to 16 byte boundary

> +	.2byte	0

> +	.8byte	.Ltext0	// Address

> +	.8byte	.Letext0-.Ltext0	// Length

> +	.8byte	.LFB4	// Address

> +	.8byte	.LFE4-.LFB4	// Length

> +	.8byte	0

> +	.8byte	0

> +	.section	.debug_ranges,"",@progbits

> +.Ldebug_ranges0:

> +	.8byte	.Ltext0	// Offset 0

> +	.8byte	.Letext0

> +	.8byte	.LFB4	// Offset 0x10

> +	.8byte	.LFE4

> +	.8byte	0

> +	.8byte	0

> +	.section	.debug_line,"",@progbits

> +.Ldebug_line0:

> +	.section	.debug_str,"MS",@progbits,1

> +.LASF6:

> +	.string	"bar_1"

> +.LASF2:

> +	.string	"tailcall-only.c"

> +.LASF3:

> +	.string	"/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +.LASF5:

> +	.string	"answer"

> +.LASF4:

> +	.string	"main"

> +.LASF1:

> +	.string	"GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"

> +.LASF0:

> +	.string	"foo_1"

> +	.ident	"GCC: (Debian 10.2.1-3) 10.2.1 20201224"

> +	.section	.note.GNU-stack,"",@progbits

> diff --git a/gdb/testsuite/gdb.btrace/aarch64-tailcall.S b/gdb/testsuite/gdb.btrace/aarch64-tailcall.S

> new file mode 100644

> index 00000000000..2023b878a1a

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/aarch64-tailcall.S

> @@ -0,0 +1,408 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.

> +

> +   This file has been generated on an armv8 machine using:

> +   gcc -S -O2 -dA -g tailcall.c -o aarch64-tailcall.S  */

> +

> +	.arch armv8-a

> +	.file	"tailcall.c"

> +	.text

> +.Ltext0:

> +	.align	2

> +	.p2align 4,,11

> +	//.tune generic

> +	.type	bar, %function

> +bar:

> +.LFB0:

> +	.file 1 "tailcall.c"

> +	// tailcall.c:22:1

> +	.loc 1 22 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall.c:23:3

> +	.loc 1 23 3 view .LVU1

> +	// tailcall.c:24:1

> +	.loc 1 24 1 is_stmt 0 view .LVU2

> +	mov	w0, 42

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally)

> +	ret

> +	.cfi_endproc

> +.LFE0:

> +	.size	bar, .-bar

> +	.align	2

> +	.p2align 4,,11

> +	.type	foo, %function

> +foo:

> +.LFB1:

> +	// tailcall.c:28:1

> +	.loc 1 28 1 is_stmt 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall.c:29:3

> +	.loc 1 29 3 view .LVU4

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)

> +	// tailcall.c:29:10

> +	.loc 1 29 10 is_stmt 0 view .LVU5

> +	b	bar

> +.LVL0:

> +	.cfi_endproc

> +.LFE1:

> +	.size	foo, .-foo

> +	.section	.text.startup,"ax",@progbits

> +	.align	2

> +	.p2align 4,,11

> +	.global	main

> +	.type	main, %function

> +main:

> +.LFB2:

> +	// tailcall.c:34:1

> +	.loc 1 34 1 is_stmt 1 view -0

> +	.cfi_startproc

> +// BLOCK 2, count:1073741824 (estimated locally) seq:0

> +// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)

> +	// tailcall.c:35:3

> +	.loc 1 35 3 view .LVU7

> +	// tailcall.c:37:3

> +	.loc 1 37 3 view .LVU8

> +	// tailcall.c:34:1

> +	.loc 1 34 1 is_stmt 0 view .LVU9

> +	stp	x29, x30, [sp, -16]!

> +	.cfi_def_cfa_offset 16

> +	.cfi_offset 29, -16

> +	.cfi_offset 30, -8

> +	mov	x29, sp

> +	// tailcall.c:37:12

> +	.loc 1 37 12 view .LVU10

> +	bl	foo

> +.LVL1:

> +	// DEBUG answer => x0

> +	// tailcall.c:38:3

> +	.loc 1 38 3 is_stmt 1 view .LVU11

> +	// DEBUG answer => x0+0x1

> +	// tailcall.c:40:3

> +	.loc 1 40 3 view .LVU12

> +	// tailcall.c:41:1

> +	.loc 1 41 1 is_stmt 0 view .LVU13

> +	add	w0, w0, 1

> +.LVL2:

> +	// DEBUG answer => x0

> +	// tailcall.c:41:1

> +	.loc 1 41 1 view .LVU14

> +	ldp	x29, x30, [sp], 16

> +	.cfi_restore 30

> +	.cfi_restore 29

> +	.cfi_def_cfa_offset 0

> +// SUCC: EXIT [always]  count:1073741824 (estimated locally)

> +	ret

> +	.cfi_endproc

> +.LFE2:

> +	.size	main, .-main

> +	.text

> +.Letext0:

> +	.section	.debug_info,"",@progbits

> +.Ldebug_info0:

> +	.4byte	0xbf	// Length of Compilation Unit Info

> +	.2byte	0x4	// DWARF version number

> +	.4byte	.Ldebug_abbrev0	// Offset Into Abbrev. Section

> +	.byte	0x8	// Pointer Size (in bytes)

> +	.uleb128 0x1	// (DIE (0xb) DW_TAG_compile_unit)

> +	.4byte	.LASF0	// DW_AT_producer: "GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"

> +	.byte	0xc	// DW_AT_language

> +	.4byte	.LASF1	// DW_AT_name: "tailcall.c"

> +	.4byte	.LASF2	// DW_AT_comp_dir: "/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +	.4byte	.Ldebug_ranges0+0	// DW_AT_ranges

> +	.8byte	0	// DW_AT_low_pc

> +	.4byte	.Ldebug_line0	// DW_AT_stmt_list

> +	.uleb128 0x2	// (DIE (0x29) DW_TAG_subprogram)

> +			// DW_AT_external

> +	.4byte	.LASF3	// DW_AT_name: "main"

> +	.byte	0x1	// DW_AT_decl_file (tailcall.c)

> +	.byte	0x21	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB2	// DW_AT_low_pc

> +	.8byte	.LFE2-.LFB2	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.4byte	0x6d	// DW_AT_sibling

> +	.uleb128 0x3	// (DIE (0x4b) DW_TAG_variable)

> +	.4byte	.LASF4	// DW_AT_name: "answer"

> +	.byte	0x1	// DW_AT_decl_file (tailcall.c)

> +	.byte	0x23	// DW_AT_decl_line

> +	.byte	0x7	// DW_AT_decl_column

> +	.4byte	0x6d	// DW_AT_type

> +	.4byte	.LLST0	// DW_AT_location

> +	.4byte	.LVUS0	// DW_AT_GNU_locviews

> +	.uleb128 0x4	// (DIE (0x5f) DW_TAG_GNU_call_site)

> +	.8byte	.LVL1	// DW_AT_low_pc

> +	.4byte	0x74	// DW_AT_abstract_origin

> +	.byte	0	// end of children of DIE 0x29

> +	.uleb128 0x5	// (DIE (0x6d) DW_TAG_base_type)

> +	.byte	0x4	// DW_AT_byte_size

> +	.byte	0x5	// DW_AT_encoding

> +	.ascii "int\0"	// DW_AT_name

> +	.uleb128 0x6	// (DIE (0x74) DW_TAG_subprogram)

> +	.ascii "foo\0"	// DW_AT_name

> +	.byte	0x1	// DW_AT_decl_file (tailcall.c)

> +	.byte	0x1b	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB1	// DW_AT_low_pc

> +	.8byte	.LFE1-.LFB1	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.4byte	0xa4	// DW_AT_sibling

> +	.uleb128 0x7	// (DIE (0x96) DW_TAG_GNU_call_site)

> +	.8byte	.LVL0	// DW_AT_low_pc

> +			// DW_AT_GNU_tail_call

> +	.4byte	0xa4	// DW_AT_abstract_origin

> +	.byte	0	// end of children of DIE 0x74

> +	.uleb128 0x8	// (DIE (0xa4) DW_TAG_subprogram)

> +	.ascii "bar\0"	// DW_AT_name

> +	.byte	0x1	// DW_AT_decl_file (tailcall.c)

> +	.byte	0x15	// DW_AT_decl_line

> +	.byte	0x1	// DW_AT_decl_column

> +			// DW_AT_prototyped

> +	.4byte	0x6d	// DW_AT_type

> +	.8byte	.LFB0	// DW_AT_low_pc

> +	.8byte	.LFE0-.LFB0	// DW_AT_high_pc

> +	.uleb128 0x1	// DW_AT_frame_base

> +	.byte	0x9c	// DW_OP_call_frame_cfa

> +			// DW_AT_GNU_all_call_sites

> +	.byte	0	// end of children of DIE 0xb

> +	.section	.debug_abbrev,"",@progbits

> +.Ldebug_abbrev0:

> +	.uleb128 0x1	// (abbrev code)

> +	.uleb128 0x11	// (TAG: DW_TAG_compile_unit)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x25	// (DW_AT_producer)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x13	// (DW_AT_language)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x1b	// (DW_AT_comp_dir)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x55	// (DW_AT_ranges)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x10	// (DW_AT_stmt_list)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x2	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x3f	// (DW_AT_external)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x1	// (DW_AT_sibling)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x3	// (abbrev code)

> +	.uleb128 0x34	// (TAG: DW_TAG_variable)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0xe	// (DW_FORM_strp)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x2	// (DW_AT_location)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.uleb128 0x2137	// (DW_AT_GNU_locviews)

> +	.uleb128 0x17	// (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x4	// (abbrev code)

> +	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x31	// (DW_AT_abstract_origin)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x5	// (abbrev code)

> +	.uleb128 0x24	// (TAG: DW_TAG_base_type)

> +	.byte	0	// DW_children_no

> +	.uleb128 0xb	// (DW_AT_byte_size)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3e	// (DW_AT_encoding)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0x8	// (DW_FORM_string)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x6	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0x1	// DW_children_yes

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0x8	// (DW_FORM_string)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x1	// (DW_AT_sibling)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x7	// (abbrev code)

> +	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x2115	// (DW_AT_GNU_tail_call)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x31	// (DW_AT_abstract_origin)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x8	// (abbrev code)

> +	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)

> +	.byte	0	// DW_children_no

> +	.uleb128 0x3	// (DW_AT_name)

> +	.uleb128 0x8	// (DW_FORM_string)

> +	.uleb128 0x3a	// (DW_AT_decl_file)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x3b	// (DW_AT_decl_line)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x39	// (DW_AT_decl_column)

> +	.uleb128 0xb	// (DW_FORM_data1)

> +	.uleb128 0x27	// (DW_AT_prototyped)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.uleb128 0x49	// (DW_AT_type)

> +	.uleb128 0x13	// (DW_FORM_ref4)

> +	.uleb128 0x11	// (DW_AT_low_pc)

> +	.uleb128 0x1	// (DW_FORM_addr)

> +	.uleb128 0x12	// (DW_AT_high_pc)

> +	.uleb128 0x7	// (DW_FORM_data8)

> +	.uleb128 0x40	// (DW_AT_frame_base)

> +	.uleb128 0x18	// (DW_FORM_exprloc)

> +	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	// (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.byte	0

> +	.section	.debug_loc,"",@progbits

> +.Ldebug_loc0:

> +.LVUS0:

> +	.uleb128 .LVU11	// View list begin (*.LVUS0)

> +	.uleb128 .LVU12	// View list end (*.LVUS0)

> +	.uleb128 .LVU12	// View list begin (*.LVUS0)

> +	.uleb128 .LVU14	// View list end (*.LVUS0)

> +	.uleb128 .LVU14	// View list begin (*.LVUS0)

> +	.uleb128 0	// View list end (*.LVUS0)

> +.LLST0:

> +	.8byte	.LVL1	// Location list begin address (*.LLST0)

> +	.8byte	.LVL1	// Location list end address (*.LLST0)

> +	.2byte	0x1	// Location expression size

> +	.byte	0x50	// DW_OP_reg0

> +	.8byte	.LVL1	// Location list begin address (*.LLST0)

> +	.8byte	.LVL2	// Location list end address (*.LLST0)

> +	.2byte	0x3	// Location expression size

> +	.byte	0x70	// DW_OP_breg0

> +	.sleb128 1

> +	.byte	0x9f	// DW_OP_stack_value

> +	.8byte	.LVL2	// Location list begin address (*.LLST0)

> +	.8byte	.LFE2	// Location list end address (*.LLST0)

> +	.2byte	0x1	// Location expression size

> +	.byte	0x50	// DW_OP_reg0

> +	.8byte	0	// Location list terminator begin (*.LLST0)

> +	.8byte	0	// Location list terminator end (*.LLST0)

> +	.section	.debug_aranges,"",@progbits

> +	.4byte	0x3c	// Length of Address Ranges Info

> +	.2byte	0x2	// DWARF aranges version

> +	.4byte	.Ldebug_info0	// Offset of Compilation Unit Info

> +	.byte	0x8	// Size of Address

> +	.byte	0	// Size of Segment Descriptor

> +	.2byte	0	// Pad to 16 byte boundary

> +	.2byte	0

> +	.8byte	.Ltext0	// Address

> +	.8byte	.Letext0-.Ltext0	// Length

> +	.8byte	.LFB2	// Address

> +	.8byte	.LFE2-.LFB2	// Length

> +	.8byte	0

> +	.8byte	0

> +	.section	.debug_ranges,"",@progbits

> +.Ldebug_ranges0:

> +	.8byte	.Ltext0	// Offset 0

> +	.8byte	.Letext0

> +	.8byte	.LFB2	// Offset 0x10

> +	.8byte	.LFE2

> +	.8byte	0

> +	.8byte	0

> +	.section	.debug_line,"",@progbits

> +.Ldebug_line0:

> +	.section	.debug_str,"MS",@progbits,1

> +.LASF0:

> +	.string	"GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"

> +.LASF2:

> +	.string	"/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +.LASF4:

> +	.string	"answer"

> +.LASF1:

> +	.string	"tailcall.c"

> +.LASF3:

> +	.string	"main"

> +	.ident	"GCC: (Debian 10.2.1-3) 10.2.1 20201224"

> +	.section	.note.GNU-stack,"",@progbits

> diff --git a/gdb/testsuite/gdb.btrace/arm-instruction_history.S b/gdb/testsuite/gdb.btrace/arm-instruction_history.S

> new file mode 100644

> index 00000000000..16ef0356993

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/arm-instruction_history.S

> @@ -0,0 +1,31 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.  */

> +

> +.arm

> +.text

> +.globl loop

> +.type  loop, %function

> +loop:

> +	movs r0, #2 /* bp.1 */

> +L1:

> +	cmp r0, #0

> +	beq L2

> +	subs r0, r0, #1

> +	b L1

> +L2:

> +	bx lr /* bp.2 */

> +

> diff --git a/gdb/testsuite/gdb.btrace/arm-record_goto.S b/gdb/testsuite/gdb.btrace/arm-record_goto.S

> new file mode 100644

> index 00000000000..d68f1187a74

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/arm-record_goto.S

> @@ -0,0 +1,432 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.

> +

> +   This file has been generated on an armv7 machine using:

> +   gcc -S -dA -g record_goto.c -o arm-record_goto.S  */

> +

> +	.arch armv7-a

> +	.eabi_attribute 28, 1	@ Tag_ABI_VFP_args

> +	.eabi_attribute 20, 1	@ Tag_ABI_FP_denormal

> +	.eabi_attribute 21, 1	@ Tag_ABI_FP_exceptions

> +	.eabi_attribute 23, 3	@ Tag_ABI_FP_number_model

> +	.eabi_attribute 24, 1	@ Tag_ABI_align8_needed

> +	.eabi_attribute 25, 1	@ Tag_ABI_align8_preserved

> +	.eabi_attribute 26, 2	@ Tag_ABI_enum_size

> +	.eabi_attribute 30, 6	@ Tag_ABI_optimization_goals

> +	.eabi_attribute 34, 1	@ Tag_CPU_unaligned_access

> +	.eabi_attribute 18, 4	@ Tag_ABI_PCS_wchar_t

> +	.file	"record_goto.c"

> +	.text

> +.Ltext0:

> +	.cfi_sections	.debug_frame

> +	.align	1

> +	.global	fun1

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	fun1, %function

> +fun1:

> +.LFB0:

> +	.file 1 "record_goto.c"

> +	@ record_goto.c:22

> +	.loc 1 22 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 1, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 seq:0

> +@ PRED: ENTRY (FALLTHRU)

> +	push	{r7}

> +	.cfi_def_cfa_offset 4

> +	.cfi_offset 7, -4

> +	add	r7, sp, #0

> +	.cfi_def_cfa_register 7

> +	@ record_goto.c:23

> +	.loc 1 23 0

> +	nop

> +	mov	sp, r7

> +	.cfi_def_cfa_register 13

> +	@ sp needed

> +	ldr	r7, [sp], #4

> +	.cfi_restore 7

> +	.cfi_def_cfa_offset 0

> +@ SUCC: EXIT [100.0%] 

> +	bx	lr

> +	.cfi_endproc

> +.LFE0:

> +	.size	fun1, .-fun1

> +	.align	1

> +	.global	fun2

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	fun2, %function

> +fun2:

> +.LFB1:

> +	@ record_goto.c:27

> +	.loc 1 27 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 1, uses_anonymous_args = 0

> +@ BLOCK 2 seq:0

> +@ PRED: ENTRY (FALLTHRU)

> +	push	{r7, lr}

> +	.cfi_def_cfa_offset 8

> +	.cfi_offset 7, -8

> +	.cfi_offset 14, -4

> +	add	r7, sp, #0

> +	.cfi_def_cfa_register 7

> +	@ record_goto.c:28

> +	.loc 1 28 0

> +	bl	fun1(PLT)

> +	@ record_goto.c:29

> +	.loc 1 29 0

> +	nop

> +@ SUCC: EXIT [100.0%] 

> +	pop	{r7, pc}

> +	.cfi_endproc

> +.LFE1:

> +	.size	fun2, .-fun2

> +	.align	1

> +	.global	fun3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	fun3, %function

> +fun3:

> +.LFB2:

> +	@ record_goto.c:33

> +	.loc 1 33 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 1, uses_anonymous_args = 0

> +@ BLOCK 2 seq:0

> +@ PRED: ENTRY (FALLTHRU)

> +	push	{r7, lr}

> +	.cfi_def_cfa_offset 8

> +	.cfi_offset 7, -8

> +	.cfi_offset 14, -4

> +	add	r7, sp, #0

> +	.cfi_def_cfa_register 7

> +	@ record_goto.c:34

> +	.loc 1 34 0

> +	bl	fun1(PLT)

> +	@ record_goto.c:35

> +	.loc 1 35 0

> +	bl	fun2(PLT)

> +	@ record_goto.c:36

> +	.loc 1 36 0

> +	nop

> +@ SUCC: EXIT [100.0%] 

> +	pop	{r7, pc}

> +	.cfi_endproc

> +.LFE2:

> +	.size	fun3, .-fun3

> +	.align	1

> +	.global	fun4

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	fun4, %function

> +fun4:

> +.LFB3:

> +	@ record_goto.c:40

> +	.loc 1 40 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 1, uses_anonymous_args = 0

> +@ BLOCK 2 seq:0

> +@ PRED: ENTRY (FALLTHRU)

> +	push	{r7, lr}

> +	.cfi_def_cfa_offset 8

> +	.cfi_offset 7, -8

> +	.cfi_offset 14, -4

> +	add	r7, sp, #0

> +	.cfi_def_cfa_register 7

> +	@ record_goto.c:41

> +	.loc 1 41 0

> +	bl	fun1(PLT)

> +	@ record_goto.c:42

> +	.loc 1 42 0

> +	bl	fun2(PLT)

> +	@ record_goto.c:43

> +	.loc 1 43 0

> +	bl	fun3(PLT)

> +	@ record_goto.c:44

> +	.loc 1 44 0

> +	nop

> +@ SUCC: EXIT [100.0%] 

> +	pop	{r7, pc}

> +	.cfi_endproc

> +.LFE3:

> +	.size	fun4, .-fun4

> +	.align	1

> +	.global	main

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	main, %function

> +main:

> +.LFB4:

> +	@ record_goto.c:48

> +	.loc 1 48 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 1, uses_anonymous_args = 0

> +@ BLOCK 2 seq:0

> +@ PRED: ENTRY (FALLTHRU)

> +	push	{r7, lr}

> +	.cfi_def_cfa_offset 8

> +	.cfi_offset 7, -8

> +	.cfi_offset 14, -4

> +	add	r7, sp, #0

> +	.cfi_def_cfa_register 7

> +	@ record_goto.c:49

> +	.loc 1 49 0

> +	bl	fun4(PLT)

> +	@ record_goto.c:50

> +	.loc 1 50 0

> +	movs	r3, #0

> +	@ record_goto.c:51

> +	.loc 1 51 0

> +	mov	r0, r3

> +@ SUCC: EXIT [100.0%] 

> +	pop	{r7, pc}

> +	.cfi_endproc

> +.LFE4:

> +	.size	main, .-main

> +.Letext0:

> +	.section	.debug_info,"",%progbits

> +.Ldebug_info0:

> +	.4byte	0x82	@ Length of Compilation Unit Info

> +	.2byte	0x4	@ DWARF version number

> +	.4byte	.Ldebug_abbrev0	@ Offset Into Abbrev. Section

> +	.byte	0x4	@ Pointer Size (in bytes)

> +	.uleb128 0x1	@ (DIE (0xb) DW_TAG_compile_unit)

> +	.4byte	.LASF4	@ DW_AT_producer: "GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -fstack-protector-strong"

> +	.byte	0xc	@ DW_AT_language

> +	.4byte	.LASF5	@ DW_AT_name: "record_goto.c"

> +	.4byte	.LASF6	@ DW_AT_comp_dir: "/home/ubuntu/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +	.4byte	.Ltext0	@ DW_AT_low_pc

> +	.4byte	.Letext0-.Ltext0	@ DW_AT_high_pc

> +	.4byte	.Ldebug_line0	@ DW_AT_stmt_list

> +	.uleb128 0x2	@ (DIE (0x25) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF7	@ DW_AT_name: "main"

> +	.byte	0x1	@ DW_AT_decl_file (record_goto.c)

> +	.byte	0x2f	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x3a	@ DW_AT_type

> +	.4byte	.LFB4	@ DW_AT_low_pc

> +	.4byte	.LFE4-.LFB4	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x3	@ (DIE (0x3a) DW_TAG_base_type)

> +	.byte	0x4	@ DW_AT_byte_size

> +	.byte	0x5	@ DW_AT_encoding

> +	.ascii "int\0"	@ DW_AT_name

> +	.uleb128 0x4	@ (DIE (0x41) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF0	@ DW_AT_name: "fun4"

> +	.byte	0x1	@ DW_AT_decl_file (record_goto.c)

> +	.byte	0x27	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	.LFB3	@ DW_AT_low_pc

> +	.4byte	.LFE3-.LFB3	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x4	@ (DIE (0x52) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF1	@ DW_AT_name: "fun3"

> +	.byte	0x1	@ DW_AT_decl_file (record_goto.c)

> +	.byte	0x20	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	.LFB2	@ DW_AT_low_pc

> +	.4byte	.LFE2-.LFB2	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x4	@ (DIE (0x63) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF2	@ DW_AT_name: "fun2"

> +	.byte	0x1	@ DW_AT_decl_file (record_goto.c)

> +	.byte	0x1a	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	.LFB1	@ DW_AT_low_pc

> +	.4byte	.LFE1-.LFB1	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_tail_call_sites

> +	.uleb128 0x5	@ (DIE (0x74) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF3	@ DW_AT_name: "fun1"

> +	.byte	0x1	@ DW_AT_decl_file (record_goto.c)

> +	.byte	0x15	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	.LFB0	@ DW_AT_low_pc

> +	.4byte	.LFE0-.LFB0	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.byte	0	@ end of children of DIE 0xb

> +	.section	.debug_abbrev,"",%progbits

> +.Ldebug_abbrev0:

> +	.uleb128 0x1	@ (abbrev code)

> +	.uleb128 0x11	@ (TAG: DW_TAG_compile_unit)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x25	@ (DW_AT_producer)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x13	@ (DW_AT_language)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x1b	@ (DW_AT_comp_dir)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x10	@ (DW_AT_stmt_list)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x2	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3f	@ (DW_AT_external)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2116	@ (DW_AT_GNU_all_tail_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x3	@ (abbrev code)

> +	.uleb128 0x24	@ (TAG: DW_TAG_base_type)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0xb	@ (DW_AT_byte_size)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3e	@ (DW_AT_encoding)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0x8	@ (DW_FORM_string)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x4	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3f	@ (DW_AT_external)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2116	@ (DW_AT_GNU_all_tail_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x5	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3f	@ (DW_AT_external)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.byte	0

> +	.section	.debug_aranges,"",%progbits

> +	.4byte	0x1c	@ Length of Address Ranges Info

> +	.2byte	0x2	@ DWARF Version

> +	.4byte	.Ldebug_info0	@ Offset of Compilation Unit Info

> +	.byte	0x4	@ Size of Address

> +	.byte	0	@ Size of Segment Descriptor

> +	.2byte	0	@ Pad to 8 byte boundary

> +	.2byte	0

> +	.4byte	.Ltext0	@ Address

> +	.4byte	.Letext0-.Ltext0	@ Length

> +	.4byte	0

> +	.4byte	0

> +	.section	.debug_line,"",%progbits

> +.Ldebug_line0:

> +	.section	.debug_str,"MS",%progbits,1

> +.LASF5:

> +	.ascii	"record_goto.c\000"

> +.LASF2:

> +	.ascii	"fun2\000"

> +.LASF6:

> +	.ascii	"/home/ubuntu/development/gdb/binutils-gdb/gdb/tests"

> +	.ascii	"uite/gdb.btrace\000"

> +.LASF4:

> +	.ascii	"GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu"

> +	.ascii	"=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -fstack-pro"

> +	.ascii	"tector-strong\000"

> +.LASF0:

> +	.ascii	"fun4\000"

> +.LASF3:

> +	.ascii	"fun1\000"

> +.LASF7:

> +	.ascii	"main\000"

> +.LASF1:

> +	.ascii	"fun3\000"

> +	.ident	"GCC: (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0"

> +	.section	.note.GNU-stack,"",%progbits

> diff --git a/gdb/testsuite/gdb.btrace/arm-tailcall-only.S b/gdb/testsuite/gdb.btrace/arm-tailcall-only.S

> new file mode 100644

> index 00000000000..73a89c6e533

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/arm-tailcall-only.S

> @@ -0,0 +1,503 @@

> +/* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2016-2020 Free Software Foundation, Inc.

> +

> +   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/>.

> +

> +   This file has been generated on an armv7 machine using:

> +   gcc -S -O2 -dA -g tailcall-only.c -o arm-tailcall-only.S  */

> +

> +	.eabi_attribute 28, 1	@ Tag_ABI_VFP_args

> +	.eabi_attribute 20, 1	@ Tag_ABI_FP_denormal

> +	.eabi_attribute 21, 1	@ Tag_ABI_FP_exceptions

> +	.eabi_attribute 23, 3	@ Tag_ABI_FP_number_model

> +	.eabi_attribute 24, 1	@ Tag_ABI_align8_needed

> +	.eabi_attribute 25, 1	@ Tag_ABI_align8_preserved

> +	.eabi_attribute 26, 2	@ Tag_ABI_enum_size

> +	.eabi_attribute 30, 2	@ Tag_ABI_optimization_goals

> +	.eabi_attribute 34, 1	@ Tag_CPU_unaligned_access

> +	.eabi_attribute 18, 4	@ Tag_ABI_PCS_wchar_t

> +	.file	"tailcall-only.c"

> +	.text

> +.Ltext0:

> +	.cfi_sections	.debug_frame

> +	.align	1

> +	.p2align 2,,3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	bar_1, %function

> +bar_1:

> +.LFB0:

> +	.file 1 "tailcall-only.c"

> +	@ tailcall-only.c:22

> +	.loc 1 22 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +	@ tailcall-only.c:24

> +	.loc 1 24 0

> +	movs	r0, #42

> +@ SUCC: EXIT [100.0%] 

> +	bx	lr

> +	.cfi_endproc

> +.LFE0:

> +	.size	bar_1, .-bar_1

> +	.align	1

> +	.p2align 2,,3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	bar, %function

> +bar:

> +.LFB1:

> +	@ tailcall-only.c:28

> +	.loc 1 28 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)

> +	@ tailcall-only.c:29

> +	.loc 1 29 0

> +	b	bar_1(PLT)

> +.LVL0:

> +	.cfi_endproc

> +.LFE1:

> +	.size	bar, .-bar

> +	.align	1

> +	.p2align 2,,3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	foo_1, %function

> +foo_1:

> +.LFB2:

> +	@ tailcall-only.c:34

> +	.loc 1 34 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)

> +	@ tailcall-only.c:35

> +	.loc 1 35 0

> +	b	bar(PLT)

> +.LVL1:

> +	.cfi_endproc

> +.LFE2:

> +	.size	foo_1, .-foo_1

> +	.align	1

> +	.p2align 2,,3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	foo, %function

> +foo:

> +.LFB3:

> +	@ tailcall-only.c:40

> +	.loc 1 40 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)

> +	@ tailcall-only.c:41

> +	.loc 1 41 0

> +	b	foo_1(PLT)

> +.LVL2:

> +	.cfi_endproc

> +.LFE3:

> +	.size	foo, .-foo

> +	.section	.text.startup,"ax",%progbits

> +	.align	1

> +	.p2align 2,,3

> +	.global	main

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	main, %function

> +main:

> +.LFB4:

> +	@ tailcall-only.c:46

> +	.loc 1 46 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +	push	{r3, lr}

> +	.cfi_def_cfa_offset 8

> +	.cfi_offset 3, -8

> +	.cfi_offset 14, -4

> +	@ tailcall-only.c:49

> +	.loc 1 49 0

> +	bl	foo(PLT)

> +.LVL3:

> +	@ tailcall-only.c:53

> +	.loc 1 53 0

> +	adds	r0, r0, #1

> +.LVL4:

> +@ SUCC: EXIT [100.0%] 

> +	pop	{r3, pc}

> +	.cfi_endproc

> +.LFE4:

> +	.size	main, .-main

> +	.text

> +.Letext0:

> +	.section	.debug_info,"",%progbits

> +.Ldebug_info0:

> +	.4byte	0xd9	@ Length of Compilation Unit Info

> +	.2byte	0x4	@ DWARF version number

> +	.4byte	.Ldebug_abbrev0	@ Offset Into Abbrev. Section

> +	.byte	0x4	@ Pointer Size (in bytes)

> +	.uleb128 0x1	@ (DIE (0xb) DW_TAG_compile_unit)

> +	.4byte	.LASF1	@ DW_AT_producer: "GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack-protector-strong"

> +	.byte	0xc	@ DW_AT_language

> +	.4byte	.LASF2	@ DW_AT_name: "tailcall-only.c"

> +	.4byte	.LASF3	@ DW_AT_comp_dir: "/home/ubuntu/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +	.4byte	.Ldebug_ranges0+0	@ DW_AT_ranges

> +	.4byte	0	@ DW_AT_low_pc

> +	.4byte	.Ldebug_line0	@ DW_AT_stmt_list

> +	.uleb128 0x2	@ (DIE (0x25) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF4	@ DW_AT_name: "main"

> +	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x2d	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB4	@ DW_AT_low_pc

> +	.4byte	.LFE4-.LFB4	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.4byte	0x57	@ DW_AT_sibling

> +	.uleb128 0x3	@ (DIE (0x3e) DW_TAG_variable)

> +	.4byte	.LASF5	@ DW_AT_name: "answer"

> +	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x2f	@ DW_AT_decl_line

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LLST0	@ DW_AT_location

> +	.uleb128 0x4	@ (DIE (0x4d) DW_TAG_GNU_call_site)

> +	.4byte	.LVL3	@ DW_AT_low_pc

> +	.4byte	0x5e	@ DW_AT_abstract_origin

> +	.byte	0	@ end of children of DIE 0x25

> +	.uleb128 0x5	@ (DIE (0x57) DW_TAG_base_type)

> +	.byte	0x4	@ DW_AT_byte_size

> +	.byte	0x5	@ DW_AT_encoding

> +	.ascii "int\0"	@ DW_AT_name

> +	.uleb128 0x6	@ (DIE (0x5e) DW_TAG_subprogram)

> +	.ascii "foo\0"	@ DW_AT_name

> +	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x27	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB3	@ DW_AT_low_pc

> +	.4byte	.LFE3-.LFB3	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.4byte	0x81	@ DW_AT_sibling

> +	.uleb128 0x7	@ (DIE (0x77) DW_TAG_GNU_call_site)

> +	.4byte	.LVL2	@ DW_AT_low_pc

> +			@ DW_AT_GNU_tail_call

> +	.4byte	0x81	@ DW_AT_abstract_origin

> +	.byte	0	@ end of children of DIE 0x5e

> +	.uleb128 0x8	@ (DIE (0x81) DW_TAG_subprogram)

> +	.4byte	.LASF0	@ DW_AT_name: "foo_1"

> +	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x21	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB2	@ DW_AT_low_pc

> +	.4byte	.LFE2-.LFB2	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.4byte	0xa4	@ DW_AT_sibling

> +	.uleb128 0x7	@ (DIE (0x9a) DW_TAG_GNU_call_site)

> +	.4byte	.LVL1	@ DW_AT_low_pc

> +			@ DW_AT_GNU_tail_call

> +	.4byte	0xa4	@ DW_AT_abstract_origin

> +	.byte	0	@ end of children of DIE 0x81

> +	.uleb128 0x6	@ (DIE (0xa4) DW_TAG_subprogram)

> +	.ascii "bar\0"	@ DW_AT_name

> +	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x1b	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB1	@ DW_AT_low_pc

> +	.4byte	.LFE1-.LFB1	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.4byte	0xc7	@ DW_AT_sibling

> +	.uleb128 0x7	@ (DIE (0xbd) DW_TAG_GNU_call_site)

> +	.4byte	.LVL0	@ DW_AT_low_pc

> +			@ DW_AT_GNU_tail_call

> +	.4byte	0xc7	@ DW_AT_abstract_origin

> +	.byte	0	@ end of children of DIE 0xa4

> +	.uleb128 0x9	@ (DIE (0xc7) DW_TAG_subprogram)

> +	.4byte	.LASF6	@ DW_AT_name: "bar_1"

> +	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)

> +	.byte	0x15	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB0	@ DW_AT_low_pc

> +	.4byte	.LFE0-.LFB0	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.byte	0	@ end of children of DIE 0xb

> +	.section	.debug_abbrev,"",%progbits

> +.Ldebug_abbrev0:

> +	.uleb128 0x1	@ (abbrev code)

> +	.uleb128 0x11	@ (TAG: DW_TAG_compile_unit)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x25	@ (DW_AT_producer)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x13	@ (DW_AT_language)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x1b	@ (DW_AT_comp_dir)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x55	@ (DW_AT_ranges)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x10	@ (DW_AT_stmt_list)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x2	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x3f	@ (DW_AT_external)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x1	@ (DW_AT_sibling)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x3	@ (abbrev code)

> +	.uleb128 0x34	@ (TAG: DW_TAG_variable)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x2	@ (DW_AT_location)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x4	@ (abbrev code)

> +	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x31	@ (DW_AT_abstract_origin)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x5	@ (abbrev code)

> +	.uleb128 0x24	@ (TAG: DW_TAG_base_type)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0xb	@ (DW_AT_byte_size)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3e	@ (DW_AT_encoding)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0x8	@ (DW_FORM_string)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x6	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0x8	@ (DW_FORM_string)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x1	@ (DW_AT_sibling)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x7	@ (abbrev code)

> +	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x2115	@ (DW_AT_GNU_tail_call)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x31	@ (DW_AT_abstract_origin)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x8	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x1	@ (DW_AT_sibling)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x9	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.byte	0

> +	.section	.debug_loc,"",%progbits

> +.Ldebug_loc0:

> +.LLST0:

> +	.4byte	.LVL3	@ Location list begin address (*.LLST0)

> +	.4byte	.LVL4	@ Location list end address (*.LLST0)

> +	.2byte	0x3	@ Location expression size

> +	.byte	0x70	@ DW_OP_breg0

> +	.sleb128 1

> +	.byte	0x9f	@ DW_OP_stack_value

> +	.4byte	.LVL4	@ Location list begin address (*.LLST0)

> +	.4byte	.LFE4	@ Location list end address (*.LLST0)

> +	.2byte	0x1	@ Location expression size

> +	.byte	0x50	@ DW_OP_reg0

> +	.4byte	0	@ Location list terminator begin (*.LLST0)

> +	.4byte	0	@ Location list terminator end (*.LLST0)

> +	.section	.debug_aranges,"",%progbits

> +	.4byte	0x24	@ Length of Address Ranges Info

> +	.2byte	0x2	@ DWARF Version

> +	.4byte	.Ldebug_info0	@ Offset of Compilation Unit Info

> +	.byte	0x4	@ Size of Address

> +	.byte	0	@ Size of Segment Descriptor

> +	.2byte	0	@ Pad to 8 byte boundary

> +	.2byte	0

> +	.4byte	.Ltext0	@ Address

> +	.4byte	.Letext0-.Ltext0	@ Length

> +	.4byte	.LFB4	@ Address

> +	.4byte	.LFE4-.LFB4	@ Length

> +	.4byte	0

> +	.4byte	0

> +	.section	.debug_ranges,"",%progbits

> +.Ldebug_ranges0:

> +	.4byte	.Ltext0	@ Offset 0

> +	.4byte	.Letext0

> +	.4byte	.LFB4	@ Offset 0x8

> +	.4byte	.LFE4

> +	.4byte	0

> +	.4byte	0

> +	.section	.debug_line,"",%progbits

> +.Ldebug_line0:

> +	.section	.debug_str,"MS",%progbits,1

> +.LASF2:

> +	.ascii	"tailcall-only.c\000"

> +.LASF5:

> +	.ascii	"answer\000"

> +.LASF1:

> +	.ascii	"GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu"

> +	.ascii	"=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack"

> +	.ascii	"-protector-strong\000"

> +.LASF4:

> +	.ascii	"main\000"

> +.LASF6:

> +	.ascii	"bar_1\000"

> +.LASF3:

> +	.ascii	"/home/ubuntu/development/gdb/binutils-gdb/gdb/tests"

> +	.ascii	"uite/gdb.btrace\000"

> +.LASF0:

> +	.ascii	"foo_1\000"

> +	.ident	"GCC: (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0"

> +	.section	.note.GNU-stack,"",%progbits

> diff --git a/gdb/testsuite/gdb.btrace/arm-tailcall.S b/gdb/testsuite/gdb.btrace/arm-tailcall.S

> new file mode 100644

> index 00000000000..2f72dd12296

> --- /dev/null

> +++ b/gdb/testsuite/gdb.btrace/arm-tailcall.S

> @@ -0,0 +1,390 @@

> + /* This testcase is part of GDB, the GNU debugger.

> +

> +   Copyright 2021 Free Software Foundation, Inc.

> +

> +   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/>.

> +

> +   This file has been generated on an armv7 machine using:

> +   gcc -S -O2 -dA -g tailcall.c -o arm-tailcall.S  */

> +

> +	.eabi_attribute 28, 1	@ Tag_ABI_VFP_args

> +	.eabi_attribute 20, 1	@ Tag_ABI_FP_denormal

> +	.eabi_attribute 21, 1	@ Tag_ABI_FP_exceptions

> +	.eabi_attribute 23, 3	@ Tag_ABI_FP_number_model

> +	.eabi_attribute 24, 1	@ Tag_ABI_align8_needed

> +	.eabi_attribute 25, 1	@ Tag_ABI_align8_preserved

> +	.eabi_attribute 26, 2	@ Tag_ABI_enum_size

> +	.eabi_attribute 30, 2	@ Tag_ABI_optimization_goals

> +	.eabi_attribute 34, 1	@ Tag_CPU_unaligned_access

> +	.eabi_attribute 18, 4	@ Tag_ABI_PCS_wchar_t

> +	.file	"tailcall.c"

> +	.text

> +.Ltext0:

> +	.cfi_sections	.debug_frame

> +	.align	1

> +	.p2align 2,,3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	bar, %function

> +bar:

> +.LFB0:

> +	.file 1 "tailcall.c"

> +	@ tailcall.c:22

> +	.loc 1 22 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +	@ tailcall.c:24

> +	.loc 1 24 0

> +	movs	r0, #42

> +@ SUCC: EXIT [100.0%] 

> +	bx	lr

> +	.cfi_endproc

> +.LFE0:

> +	.size	bar, .-bar

> +	.align	1

> +	.p2align 2,,3

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	foo, %function

> +foo:

> +.LFB1:

> +	@ tailcall.c:28

> +	.loc 1 28 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +	@ link register save eliminated.

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)

> +	@ tailcall.c:29

> +	.loc 1 29 0

> +	b	bar(PLT)

> +.LVL0:

> +	.cfi_endproc

> +.LFE1:

> +	.size	foo, .-foo

> +	.section	.text.startup,"ax",%progbits

> +	.align	1

> +	.p2align 2,,3

> +	.global	main

> +	.syntax unified

> +	.thumb

> +	.thumb_func

> +	.fpu vfpv3-d16

> +	.type	main, %function

> +main:

> +.LFB2:

> +	@ tailcall.c:34

> +	.loc 1 34 0

> +	.cfi_startproc

> +	@ args = 0, pretend = 0, frame = 0

> +	@ frame_needed = 0, uses_anonymous_args = 0

> +@ BLOCK 2 freq:10000 seq:0

> +@ PRED: ENTRY [100.0%]  (FALLTHRU)

> +	push	{r3, lr}

> +	.cfi_def_cfa_offset 8

> +	.cfi_offset 3, -8

> +	.cfi_offset 14, -4

> +	@ tailcall.c:37

> +	.loc 1 37 0

> +	bl	foo(PLT)

> +.LVL1:

> +	@ tailcall.c:41

> +	.loc 1 41 0

> +	adds	r0, r0, #1

> +.LVL2:

> +@ SUCC: EXIT [100.0%] 

> +	pop	{r3, pc}

> +	.cfi_endproc

> +.LFE2:

> +	.size	main, .-main

> +	.text

> +.Letext0:

> +	.section	.debug_info,"",%progbits

> +.Ldebug_info0:

> +	.4byte	0x93	@ Length of Compilation Unit Info

> +	.2byte	0x4	@ DWARF version number

> +	.4byte	.Ldebug_abbrev0	@ Offset Into Abbrev. Section

> +	.byte	0x4	@ Pointer Size (in bytes)

> +	.uleb128 0x1	@ (DIE (0xb) DW_TAG_compile_unit)

> +	.4byte	.LASF0	@ DW_AT_producer: "GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack-protector-strong"

> +	.byte	0xc	@ DW_AT_language

> +	.4byte	.LASF1	@ DW_AT_name: "tailcall.c"

> +	.4byte	.LASF2	@ DW_AT_comp_dir: "/home/ubuntu/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"

> +	.4byte	.Ldebug_ranges0+0	@ DW_AT_ranges

> +	.4byte	0	@ DW_AT_low_pc

> +	.4byte	.Ldebug_line0	@ DW_AT_stmt_list

> +	.uleb128 0x2	@ (DIE (0x25) DW_TAG_subprogram)

> +			@ DW_AT_external

> +	.4byte	.LASF3	@ DW_AT_name: "main"

> +	.byte	0x1	@ DW_AT_decl_file (tailcall.c)

> +	.byte	0x21	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB2	@ DW_AT_low_pc

> +	.4byte	.LFE2-.LFB2	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.4byte	0x57	@ DW_AT_sibling

> +	.uleb128 0x3	@ (DIE (0x3e) DW_TAG_variable)

> +	.4byte	.LASF4	@ DW_AT_name: "answer"

> +	.byte	0x1	@ DW_AT_decl_file (tailcall.c)

> +	.byte	0x23	@ DW_AT_decl_line

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LLST0	@ DW_AT_location

> +	.uleb128 0x4	@ (DIE (0x4d) DW_TAG_GNU_call_site)

> +	.4byte	.LVL1	@ DW_AT_low_pc

> +	.4byte	0x5e	@ DW_AT_abstract_origin

> +	.byte	0	@ end of children of DIE 0x25

> +	.uleb128 0x5	@ (DIE (0x57) DW_TAG_base_type)

> +	.byte	0x4	@ DW_AT_byte_size

> +	.byte	0x5	@ DW_AT_encoding

> +	.ascii "int\0"	@ DW_AT_name

> +	.uleb128 0x6	@ (DIE (0x5e) DW_TAG_subprogram)

> +	.ascii "foo\0"	@ DW_AT_name

> +	.byte	0x1	@ DW_AT_decl_file (tailcall.c)

> +	.byte	0x1b	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB1	@ DW_AT_low_pc

> +	.4byte	.LFE1-.LFB1	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.4byte	0x81	@ DW_AT_sibling

> +	.uleb128 0x7	@ (DIE (0x77) DW_TAG_GNU_call_site)

> +	.4byte	.LVL0	@ DW_AT_low_pc

> +			@ DW_AT_GNU_tail_call

> +	.4byte	0x81	@ DW_AT_abstract_origin

> +	.byte	0	@ end of children of DIE 0x5e

> +	.uleb128 0x8	@ (DIE (0x81) DW_TAG_subprogram)

> +	.ascii "bar\0"	@ DW_AT_name

> +	.byte	0x1	@ DW_AT_decl_file (tailcall.c)

> +	.byte	0x15	@ DW_AT_decl_line

> +			@ DW_AT_prototyped

> +	.4byte	0x57	@ DW_AT_type

> +	.4byte	.LFB0	@ DW_AT_low_pc

> +	.4byte	.LFE0-.LFB0	@ DW_AT_high_pc

> +	.uleb128 0x1	@ DW_AT_frame_base

> +	.byte	0x9c	@ DW_OP_call_frame_cfa

> +			@ DW_AT_GNU_all_call_sites

> +	.byte	0	@ end of children of DIE 0xb

> +	.section	.debug_abbrev,"",%progbits

> +.Ldebug_abbrev0:

> +	.uleb128 0x1	@ (abbrev code)

> +	.uleb128 0x11	@ (TAG: DW_TAG_compile_unit)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x25	@ (DW_AT_producer)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x13	@ (DW_AT_language)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x1b	@ (DW_AT_comp_dir)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x55	@ (DW_AT_ranges)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x10	@ (DW_AT_stmt_list)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x2	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x3f	@ (DW_AT_external)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x1	@ (DW_AT_sibling)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x3	@ (abbrev code)

> +	.uleb128 0x34	@ (TAG: DW_TAG_variable)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0xe	@ (DW_FORM_strp)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x2	@ (DW_AT_location)

> +	.uleb128 0x17	@ (DW_FORM_sec_offset)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x4	@ (abbrev code)

> +	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x31	@ (DW_AT_abstract_origin)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x5	@ (abbrev code)

> +	.uleb128 0x24	@ (TAG: DW_TAG_base_type)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0xb	@ (DW_AT_byte_size)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3e	@ (DW_AT_encoding)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0x8	@ (DW_FORM_string)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x6	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0x1	@ DW_children_yes

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0x8	@ (DW_FORM_string)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x1	@ (DW_AT_sibling)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x7	@ (abbrev code)

> +	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x2115	@ (DW_AT_GNU_tail_call)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x31	@ (DW_AT_abstract_origin)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.byte	0

> +	.byte	0

> +	.uleb128 0x8	@ (abbrev code)

> +	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)

> +	.byte	0	@ DW_children_no

> +	.uleb128 0x3	@ (DW_AT_name)

> +	.uleb128 0x8	@ (DW_FORM_string)

> +	.uleb128 0x3a	@ (DW_AT_decl_file)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x3b	@ (DW_AT_decl_line)

> +	.uleb128 0xb	@ (DW_FORM_data1)

> +	.uleb128 0x27	@ (DW_AT_prototyped)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.uleb128 0x49	@ (DW_AT_type)

> +	.uleb128 0x13	@ (DW_FORM_ref4)

> +	.uleb128 0x11	@ (DW_AT_low_pc)

> +	.uleb128 0x1	@ (DW_FORM_addr)

> +	.uleb128 0x12	@ (DW_AT_high_pc)

> +	.uleb128 0x6	@ (DW_FORM_data4)

> +	.uleb128 0x40	@ (DW_AT_frame_base)

> +	.uleb128 0x18	@ (DW_FORM_exprloc)

> +	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)

> +	.uleb128 0x19	@ (DW_FORM_flag_present)

> +	.byte	0

> +	.byte	0

> +	.byte	0

> +	.section	.debug_loc,"",%progbits

> +.Ldebug_loc0:

> +.LLST0:

> +	.4byte	.LVL1	@ Location list begin address (*.LLST0)

> +	.4byte	.LVL2	@ Location list end address (*.LLST0)

> +	.2byte	0x3	@ Location expression size

> +	.byte	0x70	@ DW_OP_breg0

> +	.sleb128 1

> +	.byte	0x9f	@ DW_OP_stack_value

> +	.4byte	.LVL2	@ Location list begin address (*.LLST0)

> +	.4byte	.LFE2	@ Location list end address (*.LLST0)

> +	.2byte	0x1	@ Location expression size

> +	.byte	0x50	@ DW_OP_reg0

> +	.4byte	0	@ Location list terminator begin (*.LLST0)

> +	.4byte	0	@ Location list terminator end (*.LLST0)

> +	.section	.debug_aranges,"",%progbits

> +	.4byte	0x24	@ Length of Address Ranges Info

> +	.2byte	0x2	@ DWARF Version

> +	.4byte	.Ldebug_info0	@ Offset of Compilation Unit Info

> +	.byte	0x4	@ Size of Address

> +	.byte	0	@ Size of Segment Descriptor

> +	.2byte	0	@ Pad to 8 byte boundary

> +	.2byte	0

> +	.4byte	.Ltext0	@ Address

> +	.4byte	.Letext0-.Ltext0	@ Length

> +	.4byte	.LFB2	@ Address

> +	.4byte	.LFE2-.LFB2	@ Length

> +	.4byte	0

> +	.4byte	0

> +	.section	.debug_ranges,"",%progbits

> +.Ldebug_ranges0:

> +	.4byte	.Ltext0	@ Offset 0

> +	.4byte	.Letext0

> +	.4byte	.LFB2	@ Offset 0x8

> +	.4byte	.LFE2

> +	.4byte	0

> +	.4byte	0

> +	.section	.debug_line,"",%progbits

> +.Ldebug_line0:

> +	.section	.debug_str,"MS",%progbits,1

> +.LASF0:

> +	.ascii	"GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu"

> +	.ascii	"=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack"

> +	.ascii	"-protector-strong\000"

> +.LASF4:

> +	.ascii	"answer\000"

> +.LASF1:

> +	.ascii	"tailcall.c\000"

> +.LASF2:

> +	.ascii	"/home/ubuntu/development/gdb/binutils-gdb/gdb/tests"

> +	.ascii	"uite/gdb.btrace\000"

> +.LASF3:

> +	.ascii	"main\000"

> +	.ident	"GCC: (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0"

> +	.section	.note.GNU-stack,"",%progbits

> diff --git a/gdb/testsuite/gdb.btrace/buffer-size.exp b/gdb/testsuite/gdb.btrace/buffer-size.exp

> index ea4e36c1593..23f859dce9c 100644

> --- a/gdb/testsuite/gdb.btrace/buffer-size.exp

> +++ b/gdb/testsuite/gdb.btrace/buffer-size.exp

> @@ -32,10 +32,17 @@ if ![runto_main] {

>      return -1

>  }

>  

> -gdb_test_no_output "set record btrace bts buffer-size 1"

> -gdb_test_no_output "set record btrace pt buffer-size 1"

> -gdb_test "show record btrace bts buffer-size" "The record/replay bts buffer size is 1\.\r"

> -gdb_test "show record btrace pt buffer-size" "The record/replay pt buffer size is 1\.\r"

> +set btrace_type ""

> +if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    set btrace_type { "bts" "pt" }

> +} elseif {[istarget "arm*-*-*"]|| [istarget "aarch64*-*-*"]} {

> +    set btrace_type { "etm" } 

> +}

> +

> +foreach_with_prefix format $btrace_type {

> +    gdb_test_no_output "set record btrace $format buffer-size 1"

> +    gdb_test "show record btrace $format buffer-size" "The record/replay $format buffer size is 1\.\r"

> +}

>  

>  gdb_test_no_output "record btrace"

>  gdb_test "info record" [multi_line \

> diff --git a/gdb/testsuite/gdb.btrace/instruction_history.exp b/gdb/testsuite/gdb.btrace/instruction_history.exp

> index 403085c083f..3a6e7362f74 100644

> --- a/gdb/testsuite/gdb.btrace/instruction_history.exp

> +++ b/gdb/testsuite/gdb.btrace/instruction_history.exp

> @@ -22,7 +22,17 @@ if { [skip_btrace_tests] } {

>      return -1

>  }

>  

> -standard_testfile .c .S

> +set test_prefix ""

> +if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    set test_prefix "x86"

> +} elseif {[istarget "arm*-*-*"]} {

> +    set test_prefix "arm"

> +} elseif {[istarget "aarch64*-*-*"]} {

> +    set test_prefix "aarch64"

> +}

> +

> +standard_testfile instruction_history.c $test_prefix-instruction_history.S

> +

>  if [prepare_for_testing "failed to prepare" $testfile "$srcfile $srcfile2" {debug}] {

>      return -1

>  }

> @@ -67,40 +77,108 @@ if { $traced != 11 } {

>      pass $message

>  }

>  

> -# test that we see the expected instructions

> -gdb_test "record instruction-history 3,7" [multi_line \

> +if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +  set test_pattern(0) "[multi_line \

>        "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "4\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tdec    %eax" \

>        "5\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "6\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \

>        "7\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \

> -  ]

> -

> -gdb_test "record instruction-history /f 3,+5" [multi_line \

> +    ]"

> +  set test_pattern(1) "[multi_line \

>        "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tdec    %eax" \

>        "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \

>        "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \

> -  ]

> -

> -gdb_test "record instruction-history /p 7,-5" [multi_line \

> +      ]"

> +  set test_pattern(2) "[multi_line \

>        "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "4\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tdec    %eax" \

>        "5\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "6\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \

>        "7\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \

> -  ]

> -

> -gdb_test "record instruction-history /pf 3,7" [multi_line \

> +      ]"

> +  set test_pattern(3) "[multi_line \

>        "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tdec    %eax" \

>        "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \

>        "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \

>        "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \

> -  ]

> +      ]"

> +  set test_pattern(4) "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r"

> +} elseif {[istarget "arm*-*-*"]} {

> +  set test_pattern(0) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \

> +      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \

> +      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \

> +      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tr0, #0" \

> +      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \

> +      ]"

> +  set test_pattern(1) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \

> +      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \

> +      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \

> +      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tr0, #0" \

> +      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \

> +      ]"

> +  set test_pattern(2) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \

> +      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \

> +      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \

> +      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tr0, #0" \

> +      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \

> +      ]"

> +  set test_pattern(3)  "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \

> +      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \

> +      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \

> +      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tr0, #0" \

> +      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \

> +      ]"

> +  set test_pattern(4) "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r"

> +} elseif {[istarget "aarch64*-*-*"]} {

> +  set test_pattern(0) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*" \

> +      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \

> +      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \

> +      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \

> +      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \

> +    ]"

> +  set test_pattern(1) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*" \

> +      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \

> +      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \

> +      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \

> +      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \

> +      ]"

> +  set test_pattern(2) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*" \

> +      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \

> +      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \

> +      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \

> +      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \

> +      ]"

> +  set test_pattern(3) "[multi_line \

> +      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\\.eq\t0x\[0-9a-f\]+ <L2>.*" \

> +      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \

> +      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \

> +      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \

> +      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \

> +      ]"

> +  set test_pattern(4) "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>  // b\.none\r"

> +}

> +

> +# test that we see the expected instructions

> +gdb_test "record instruction-history 3,7" $test_pattern(0)

> +

> +gdb_test "record instruction-history /f 3,+5" $test_pattern(1)

> +

> +gdb_test "record instruction-history /p 7,-5" $test_pattern(2)

> +

> +gdb_test "record instruction-history /pf 3,7"  $test_pattern(3)

>  

> -gdb_test "record instruction-history 3,3" "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r"

> +gdb_test "record instruction-history 3,3" $test_pattern(4)

>  

>  # the following tests are checking the iterators

>  # to avoid lots of regexps, we just check the number of lines that

> diff --git a/gdb/testsuite/gdb.btrace/non-stop.exp b/gdb/testsuite/gdb.btrace/non-stop.exp

> index e509d65d660..fbc4cda7dd6 100644

> --- a/gdb/testsuite/gdb.btrace/non-stop.exp

> +++ b/gdb/testsuite/gdb.btrace/non-stop.exp

> @@ -31,6 +31,12 @@ save_vars { GDBFLAGS } {

>      clean_restart $testfile

>  }

>  

> +if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    set loop_position 2

> +} elseif {[istarget "arm*-*-*"] || [istarget "aarch64*-*-*"]} {

> +    set loop_position 3

> +}

> +

>  if ![runto_main] {

>      untested "failed to run to main"

>      return -1

> @@ -111,87 +117,99 @@ gdb_test "thread apply all info rec" ".*"

>  gdb_test "info threads" ".*"

>  

>  with_test_prefix "navigate" {

> -    gdb_test "thread apply 1 record goto 3" "$loop_line"

> -    gdb_test "thread apply 2 record goto 4" "$loop_line"

> +    gdb_test "thread apply 1 record goto [expr {$loop_position + 1}]" "$loop_line"

> +    gdb_test "thread apply 2 record goto [expr {$loop_position + 2}]" "$loop_line"

>      gdb_test "thread apply 1 info record" \

> -        ".*Replay in progress\.  At instruction 3\." "thread 1 at insn 3"

> +        ".*Replay in progress\.  At instruction [expr {$loop_position + 1}]\." "thread 1 at insn $loop_position"

>      gdb_test "thread apply 2 info record" \

> -        ".*Replay in progress\.  At instruction 4\." "thread 2 at insn 4"

> +        ".*Replay in progress\.  At instruction [expr {$loop_position + 2}]\." "thread 2 at insn [expr {$loop_position + 2}]"

>  

> -    gdb_test "thread apply all record goto 5" "$loop_line"

> +    gdb_test "thread apply all record goto [expr {$loop_position + 3}]" "$loop_line"

>      gdb_test "thread apply 1 info record" \

> -        ".*Replay in progress\.  At instruction 5\." "thread 1 at insn 5"

> +        ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\." "thread 1 at insn [expr {$loop_position + 3}]"

>      gdb_test "thread apply 2 info record" \

> -        ".*Replay in progress\.  At instruction 5\." "thread 2 at insn 5"

> +        ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\." "thread 2 at insn [expr {$loop_position + 3}]"

>  }

>  

>  with_test_prefix "step" {

> +    with_test_prefix "fixture" {

> +	gdb_test "thread apply 1 record goto [expr {$loop_position + 3}]" ".*"

> +	gdb_test "thread apply 2 record goto [expr {$loop_position + 3}]" ".*"

> +    }

>      with_test_prefix "thread 1" {

>          gdb_test "thread apply 1 stepi 2" "$loop_line"

>          gdb_test "thread apply 1 info record" \

> -            ".*Replay in progress\.  At instruction 7\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 5}]\."

>          gdb_test "thread apply 2 info record" \

> -            ".*Replay in progress\.  At instruction 5\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."

>      }

>  

>      with_test_prefix "thread 2" {

>          gdb_test "thread apply 2 stepi 3" "$loop_line"

>          gdb_test "thread apply 1 info record" \

> -            ".*Replay in progress\.  At instruction 7\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 5}]\."

>          gdb_test "thread apply 2 info record" \

> -            ".*Replay in progress\.  At instruction 8\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 6}]\."

>      }

>  

>      with_test_prefix "all" {

>          gdb_cont_to all "stepi 4" "$loop_line" 2

>          gdb_test "thread apply 1 info record" \

> -            ".*Replay in progress\.  At instruction 11\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 9}]\."

>          gdb_test "thread apply 2 info record" \

> -            ".*Replay in progress\.  At instruction 12\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 10}]\."

>      }

>  }

>  

>  with_test_prefix "reverse-step" {

> +    with_test_prefix "fixture" {

> +        gdb_test "thread apply 1 record goto [expr {$loop_position + 9}]" ".*"

> +        gdb_test "thread apply 2 record goto [expr {$loop_position + 10}]" ".*"

> +    }

>      with_test_prefix "thread 1" {

>          gdb_test "thread apply 1 reverse-stepi 2" "$loop_line"

>          gdb_test "thread apply 1 info record" \

> -            ".*Replay in progress\.  At instruction 9\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 7}]\."

>          gdb_test "thread apply 2 info record" \

> -            ".*Replay in progress\.  At instruction 12\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 10}]\."

>      }

>  

>      with_test_prefix "thread 2" {

>          gdb_test "thread apply 2 reverse-stepi 3" "$loop_line"

>          gdb_test "thread apply 1 info record" \

> -            ".*Replay in progress\.  At instruction 9\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 7}]\."

>          gdb_test "thread apply 2 info record" \

> -            ".*Replay in progress\.  At instruction 9\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 7}]\."

>      }

>  

>      with_test_prefix "all" {

>          gdb_cont_to all "reverse-stepi 4" "$loop_line" 2

>          gdb_test "thread apply 1 info record" \

> -            ".*Replay in progress\.  At instruction 5\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."

>          gdb_test "thread apply 2 info record" \

> -            ".*Replay in progress\.  At instruction 5\."

> +            ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."

>      }

>  }

>  

>  with_test_prefix "continue" {

> +    with_test_prefix "fixture" {

> +	gdb_test "thread apply 1 record goto [expr {$loop_position + 3}]" ".*"

> +	gdb_test "thread apply 2 record goto [expr {$loop_position + 3}]" ".*"

> +    }

>      with_test_prefix "thread 1" {

>  	with_test_prefix "continue" {

>  	    gdb_cont_to_no_history 1 "continue" 1

>  	    gdb_test "thread apply 1 info record" \

>  		".*Recorded \[0-9\]+ instructions \[^\\\r\\\n\]*"

>  	    gdb_test "thread apply 2 info record" \

> -		".*Replay in progress\.  At instruction 5\."

> +		".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."

>  	}

>  	with_test_prefix "reverse-continue" {

>  	    gdb_cont_to_no_history 1 "reverse-continue" 1

>  	    gdb_test "thread apply 1 info record" \

>  		".*Replay in progress\.  At instruction 1\."

>  	    gdb_test "thread apply 2 info record" \

> -		".*Replay in progress\.  At instruction 5\."

> +		".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."

>  	}

>      }

>  

> diff --git a/gdb/testsuite/gdb.btrace/record_goto.exp b/gdb/testsuite/gdb.btrace/record_goto.exp

> index 75d76da1c7f..267d4b412bc 100644

> --- a/gdb/testsuite/gdb.btrace/record_goto.exp

> +++ b/gdb/testsuite/gdb.btrace/record_goto.exp

> @@ -35,21 +35,149 @@ if [info exists COMPILE] {

>      # make check RUNTESTFLAGS="gdb.btrace/record_goto.exp COMPILE=1"

>      standard_testfile record_goto.c

>      lappend opts debug

> -} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +} else {

> +  set test_prefix ""

> +  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>      if {[is_amd64_regs_target]} {

> -		standard_testfile x86_64-record_goto.S

> +      set test_prefix "x86_64"

>      } else {

> -		standard_testfile i686-record_goto.S

> +      set test_prefix "i686"

>      }

> -} else {

> +  } elseif {[istarget "arm*-*-*"]} {

> +      set test_prefix "arm"

> +  } elseif {[istarget "aarch64*-*-*"]} {

> +    set test_prefix "aarch64"

> +  } else {

>      unsupported "target architecture not supported"

>      return -1

> +  }

> +  standard_testfile $test_prefix-record_goto.S

>  }

>  

>  if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {

>      return -1

>  }

>  

> +if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    set function_positions(0) 19

> +    set function_positions(1) 27

> +    set function_positions(2) 2

> +    set function_positions(end) 40

> +    set function_positions(3) 39

> +

> +    set sequence_begin(1) 1

> +    set sequence_end(1) 1

> +    set sequence_begin(2) 2

> +    set sequence_end(2) 4

> +    set sequence_begin(3) 5

> +    set sequence_end(3) 8

> +    set sequence_begin(4) 9

> +    set sequence_end(4) 9

> +    set sequence_begin(5) 10

> +    set sequence_end(5) 12

> +    set sequence_begin(6) 13

> +    set sequence_end(6) 16

> +    set sequence_begin(7) 17

> +    set sequence_end(7) 18

> +    set sequence_begin(8) 19

> +    set sequence_end(8) 19

> +    set sequence_begin(9) 20

> +    set sequence_end(9) 22

> +    set sequence_begin(10) 23

> +    set sequence_end(10) 26

> +    set sequence_begin(11) 27

> +    set sequence_end(11) 27

> +    set sequence_begin(12) 28

> +    set sequence_end(12) 30

> +    set sequence_begin(13) 31

> +    set sequence_end(13) 34

> +    set sequence_begin(14) 35

> +    set sequence_end(14) 36

> +    set sequence_begin(15) 37

> +    set sequence_end(15) 38

> +    set sequence_begin(16) 39

> +    set sequence_end(16) 40

> +

> +} elseif {[istarget "arm*-*-*"]} {

> +    set function_positions(0) 23

> +    set function_positions(1) 33

> +    set function_positions(2) 2

> +    set function_positions(end) 48

> +    set function_positions(3) 47

> +

> +    set sequence_begin(1) 1

> +    set sequence_end(1) 1

> +    set sequence_begin(2) 2

> +    set sequence_end(2) 4

> +    set sequence_begin(3) 5

> +    set sequence_end(3) 10

> +    set sequence_begin(4) 11

> +    set sequence_end(4) 11

> +    set sequence_begin(5) 12

> +    set sequence_end(5) 14

> +    set sequence_begin(6) 15

> +    set sequence_end(6) 20

> +    set sequence_begin(7) 21

> +    set sequence_end(7) 22

> +    set sequence_begin(8) 23

> +    set sequence_end(8) 23

> +    set sequence_begin(9) 24

> +    set sequence_end(9) 26

> +    set sequence_begin(10) 27

> +    set sequence_end(10) 32

> +    set sequence_begin(11) 33

> +    set sequence_end(11) 33

> +    set sequence_begin(12) 34

> +    set sequence_end(12) 36

> +    set sequence_begin(13) 37

> +    set sequence_end(13) 42

> +    set sequence_begin(14) 43

> +    set sequence_end(14) 44

> +    set sequence_begin(15) 45

> +    set sequence_end(15) 46

> +    set sequence_begin(16) 47

> +    set sequence_end(16) 48

> +} elseif {[istarget "aarch64*-*-*"]} {

> +    set function_positions(0) 16

> +    set function_positions(1) 22

> +    set function_positions(2) 2

> +    set function_positions(end) 36

> +    set function_positions(3) 35

> +

> +    set sequence_begin(1) 1

> +    set sequence_end(1) 1

> +    set sequence_begin(2) 2

> +    set sequence_end(2) 4

> +    set sequence_begin(3) 5

> +    set sequence_end(3) 6

> +    set sequence_begin(4) 7

> +    set sequence_end(4) 7

> +    set sequence_begin(5) 8

> +    set sequence_end(5) 10

> +    set sequence_begin(6) 11

> +    set sequence_end(6) 12

> +    set sequence_begin(7) 13

> +    set sequence_end(7) 15

> +    set sequence_begin(8) 16

> +    set sequence_end(8) 16

> +    set sequence_begin(9) 17

> +    set sequence_end(9) 19

> +    set sequence_begin(10) 20

> +    set sequence_end(10) 21

> +    set sequence_begin(11) 22

> +    set sequence_end(11) 22

> +    set sequence_begin(12) 23

> +    set sequence_end(12) 25

> +    set sequence_begin(13) 26

> +    set sequence_end(13) 27

> +    set sequence_begin(14) 28

> +    set sequence_end(14) 30

> +    set sequence_begin(15) 31

> +    set sequence_end(15) 33

> +    set sequence_begin(16) 34

> +    set sequence_end(16) 36

> +}

> +

>  if ![runto_main] {

>      untested "failed to run to main"

>      return -1

> @@ -65,43 +193,43 @@ gdb_test "next"

>  

>  # start by listing all functions

>  gdb_test "record function-call-history /ci 1, +20" [multi_line \

> -  "1\tmain\tinst 1,1" \

> -  "2\t  fun4\tinst 2,4" \

> -  "3\t    fun1\tinst 5,8" \

> -  "4\t  fun4\tinst 9,9" \

> -  "5\t    fun2\tinst 10,12" \

> -  "6\t      fun1\tinst 13,16" \

> -  "7\t    fun2\tinst 17,18" \

> -  "8\t  fun4\tinst 19,19" \

> -  "9\t    fun3\tinst 20,22" \

> -  "10\t      fun1\tinst 23,26" \

> -  "11\t    fun3\tinst 27,27" \

> -  "12\t      fun2\tinst 28,30" \

> -  "13\t        fun1\tinst 31,34" \

> -  "14\t      fun2\tinst 35,36" \

> -  "15\t    fun3\tinst 37,38" \

> -  "16\t  fun4\tinst 39,40" \

> +  "1\tmain\tinst $sequence_begin(1),$sequence_end(1)" \

> +  "2\t  fun4\tinst $sequence_begin(2),$sequence_end(2)" \

> +  "3\t    fun1\tinst $sequence_begin(3),$sequence_end(3)" \

> +  "4\t  fun4\tinst $sequence_begin(4),$sequence_end(4)" \

> +  "5\t    fun2\tinst $sequence_begin(5),$sequence_end(5)" \

> +  "6\t      fun1\tinst $sequence_begin(6),$sequence_end(6)" \

> +  "7\t    fun2\tinst $sequence_begin(7),$sequence_end(7)" \

> +  "8\t  fun4\tinst $sequence_begin(8),$sequence_end(8)" \

> +  "9\t    fun3\tinst $sequence_begin(9),$sequence_end(9)" \

> +  "10\t      fun1\tinst $sequence_begin(10),$sequence_end(10)" \

> +  "11\t    fun3\tinst $sequence_begin(11),$sequence_end(11)" \

> +  "12\t      fun2\tinst $sequence_begin(12),$sequence_end(12)" \

> +  "13\t        fun1\tinst $sequence_begin(13),$sequence_end(13)" \

> +  "14\t      fun2\tinst $sequence_begin(14),$sequence_end(14)" \

> +  "15\t    fun3\tinst $sequence_begin(15),$sequence_end(15)" \

> +  "16\t  fun4\tinst $sequence_begin(16),$sequence_end(16)" \

>    ]

>  

>  # let's see if we can go back in history

> -gdb_test "record goto 19" ".*fun4 \\(\\) at record_goto.c:43.*"

> +gdb_test "record goto $function_positions(0)" ".*fun4 \\(\\) at record_goto.c:43.*"

>  

>  # the function call history should start at the new location

>  gdb_test "record function-call-history /ci" [multi_line \

> -  "8\t  fun4\tinst 19,19" \

> -  "9\t    fun3\tinst 20,22" \

> -  "10\t      fun1\tinst 23,26" \

> -  ] "function-call-history from 19 forwards"

> +  "8\t  fun4\tinst $sequence_begin(8),$sequence_end(8)" \

> +  "9\t    fun3\tinst $sequence_begin(9),$sequence_end(9)" \

> +  "10\t      fun1\tinst $sequence_begin(10),$sequence_end(10)" \

> +  ] "function-call-history from $function_positions(0) forwards"

>  

>  # the instruction history should start at the new location

>  gdb_test "record instruction-history" [multi_line \

> -  "19.*" \

> -  "20.*" \

> -  "21.*" \

> -  ] "instruction-history from 19 forwards"

> +  "$function_positions(0).*" \

> +  "[expr {$function_positions(0) + 1}].*" \

> +  "[expr {$function_positions(0) + 2}].*" \

> +  ] "instruction-history from $function_positions(0) forwards"

>  

>  # let's go to another place in the history

> -gdb_test "record goto 27" ".*fun3 \\(\\) at record_goto.c:35.*"

> +gdb_test "record goto $function_positions(1)" ".*fun3 \\(\\) at record_goto.c:35.*"

>  

>  # check the back trace at that location

>  gdb_test "backtrace" [multi_line \

> @@ -117,26 +245,26 @@ gdb_test "up" ".*main.*at record_goto.c:49.*" "up to main"

>  

>  # the function call history should start at the new location

>  gdb_test "record function-call-history /ci -" [multi_line \

> -  "9\t    fun3\tinst 20,22" \

> -  "10\t      fun1\tinst 23,26" \

> -  "11\t    fun3\tinst 27,27" \

> -  ] "function-call-history from 27 backwards"

> +  "9\t    fun3\tinst $sequence_begin(9),$sequence_end(9)" \

> +  "10\t      fun1\tinst $sequence_begin(10),$sequence_end(10)" \

> +  "11\t    fun3\tinst $sequence_begin(11),$sequence_end(11)" \

> +  ] "function-call-history from $function_positions(1) backwards"

>  

>  # the instruction history should start at the new location

>  gdb_test "record instruction-history -" [multi_line \

> -  "25.*" \

> -  "26.*" \

> -  "27.*" \

> -  ] "instruction-history from 27 backwards"

> +  "[expr {$function_positions(1) - 2}].*" \

> +  "[expr {$function_positions(1) - 1}].*" \

> +  "$function_positions(1).*" \

> +  ] "instruction-history from $function_positions(1) backwards"

>  

>  # test that we can go to the begin of the trace

>  gdb_test "record goto begin" ".*main \\(\\) at record_goto.c:49.*"

>  

>  # check that we're filling up the context correctly

>  gdb_test "record function-call-history /ci -" [multi_line \

> -  "1\tmain\tinst 1,1" \

> -  "2\t  fun4\tinst 2,4" \

> -  "3\t    fun1\tinst 5,8" \

> +  "1\tmain\tinst $sequence_begin(1),$sequence_end(1)" \

> +  "2\t  fun4\tinst $sequence_begin(2),$sequence_end(2)" \

> +  "3\t    fun1\tinst $sequence_begin(3),$sequence_end(3)" \

>    ] "function-call-history from begin backwards"

>  

>  # check that we're filling up the context correctly

> @@ -147,52 +275,53 @@ gdb_test "record instruction-history -" [multi_line \

>    ] "instruction-history from begin backwards"

>  

>  # we should get the exact same history from the first instruction

> -gdb_test "record goto 2" ".*fun4 \\(\\) at record_goto.c:40.*"

> +gdb_test "record goto $function_positions(2)" ".*fun4 \\(\\) at record_goto.c:40.*"

>  

>  # check that we're filling up the context correctly

>  gdb_test "record function-call-history /ci -" [multi_line \

> -  "1\tmain\tinst 1,1" \

> -  "2\t  fun4\tinst 2,4" \

> -  "3\t    fun1\tinst 5,8\r" \

> -  ] "function-call-history from 2 backwards"

> +  "1\tmain\tinst $sequence_begin(1),$sequence_end(1)" \

> +  "2\t  fun4\tinst $sequence_begin(2),$sequence_end(2)" \

> +  "3\t    fun1\tinst $sequence_begin(3),$sequence_end(3)\r" \

> +  ] "function-call-history from $function_positions(2) backwards"

>  

>  # check that we're filling up the context correctly

>  gdb_test "record instruction-history -" [multi_line \

>    "1.*" \

>    "2.*" \

>    "3.*" \

> -  ] "instruction-history from 2 backwards"

> +  ] "instruction-history from $function_positions(2) backwards"

>  

>  # check that we can go to the end of the trace

>  gdb_test "record goto end" ".*main \\(\\) at record_goto.c:50.*"

>  

>  # check that we're filling up the context correctly

>  gdb_test "record function-call-history /ci" [multi_line \

> -  "14\t      fun2\tinst 35,36" \

> -  "15\t    fun3\tinst 37,38" \

> -  "16\t  fun4\tinst 39,40" \

> +  "14\t      fun2\tinst $sequence_begin(14),$sequence_end(14)" \

> +  "15\t    fun3\tinst $sequence_begin(15),$sequence_end(15)" \

> +  "16\t  fun4\tinst $sequence_begin(16),$sequence_end(16)" \

>    ] "function-call-history from end forwards"

>  

>  # check that we're filling up the context correctly

> +#adapt it for arm, last instruction is  at pos 48

>  gdb_test "record instruction-history" [multi_line \

> -  "38.*" \

> -  "39.*" \

> -  "40.*\r" \

> +  "[expr {$function_positions(end) - 2}].*" \

> +  "[expr {$function_positions(end) - 1}].*" \

> +  "$function_positions(end).*\r" \

>    ] "instruction-history from end forwards"

>  

>  # we should get the exact same history from the second to last instruction

> -gdb_test "record goto 39" ".*fun4 \\(\\) at record_goto.c:44.*"

> +gdb_test "record goto $function_positions(3)" ".*fun4 \\(\\) at record_goto.c:44.*"

>  

>  # check that we're filling up the context correctly

>  gdb_test "record function-call-history /ci" [multi_line \

> -  "14\t      fun2\tinst 35,36" \

> -  "15\t    fun3\tinst 37,38" \

> -  "16\t  fun4\tinst 39,40\r" \

> -  ] "function-call-history from 39 forwards"

> +  "14\t      fun2\tinst $sequence_begin(14),$sequence_end(14)" \

> +  "15\t    fun3\tinst $sequence_begin(15),$sequence_end(15)" \

> +  "16\t  fun4\tinst $sequence_begin(16),$sequence_end(16)\r" \

> +  ] "function-call-history from $function_positions(3) forwards"

>  

>  # check that we're filling up the context correctly

>  gdb_test "record instruction-history" [multi_line \

> -  "38.*" \

> -  "39.*" \

> -  "40.*\r" \

> -  ] "instruction-history from 39 forwards"

> +  "[expr {$function_positions(3) - 1}].*" \

> +  "$function_positions(3).*" \

> +  "[expr {$function_positions(3) + 1}].*\r" \

> +  ] "instruction-history from $function_positions(3) forwards"

> diff --git a/gdb/testsuite/gdb.btrace/stepi.exp b/gdb/testsuite/gdb.btrace/stepi.exp

> index 480c08c4875..f07961228e0 100644

> --- a/gdb/testsuite/gdb.btrace/stepi.exp

> +++ b/gdb/testsuite/gdb.btrace/stepi.exp

> @@ -33,21 +33,79 @@ if [info exists COMPILE] {

>      # make check RUNTESTFLAGS="gdb.btrace/stepi.exp COMPILE=1"

>      standard_testfile record_goto.c

>      lappend opts debug

> -} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +} else {

> +  set test_prefix ""

> +  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>      if {[is_amd64_regs_target]} {

> -		standard_testfile x86_64-record_goto.S

> +      set test_prefix "x86_64"

>      } else {

> -		standard_testfile i686-record_goto.S

> +      set test_prefix "i686"

>      }

> -} else {

> +  } elseif {[istarget "arm*-*-*"]} {

> +      set test_prefix "arm"

> +  } elseif {[istarget "aarch64*-*-*"]} {

> +    set test_prefix "aarch64"

> +  } else {

>      unsupported "target architecture not supported"

>      return -1

> +  }

> +  standard_testfile $test_prefix-record_goto.S

>  }

>  

>  if [prepare_for_testing "failed to prepare" $testfile $srcfile {}] {

>      return -1

>  }

>  

> +if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    set instructions_count 40

> +    set instruction_position(0) 39

> +    set instruction_position(1) 40

> +    set instruction_position(2) 1

> +    set instruction_position(3) 1

> +    set instruction_position(4) 22

> +    set instruction_position(5) 23

> +    set instruction_position(6) 22

> +    set instruction_position(7) 27

> +    set instruction_position(8) 22

> +    set instruction_position(9) 1

> +    set instruction_position(10) 1

> +    set instruction_position(11) 1

> +    set instruction_position(12) 2

> +    set instruction_position(13) 1

> +} elseif {[istarget "arm*-*-*"]} {

> +    set instructions_count 48

> +    set instruction_position(0) 47

> +    set instruction_position(1) 48

> +    set instruction_position(2) 1

> +    set instruction_position(3) 1

> +    set instruction_position(4) 26

> +    set instruction_position(5) 27

> +    set instruction_position(6) 26

> +    set instruction_position(7) 33

> +    set instruction_position(8) 26

> +    set instruction_position(9) 1

> +    set instruction_position(10) 1

> +    set instruction_position(11) 1

> +    set instruction_position(12) 2

> +    set instruction_position(13) 1

> +} elseif {[istarget "aarch64*-*-*"]} {

> +    set instructions_count 36

> +    set instruction_position(0) 35

> +    set instruction_position(1) 36

> +    set instruction_position(2) 1

> +    set instruction_position(3) 1

> +    set instruction_position(4) 19

> +    set instruction_position(5) 20

> +    set instruction_position(6) 19

> +    set instruction_position(7) 22

> +    set instruction_position(8) 19

> +    set instruction_position(9) 1

> +    set instruction_position(10) 1

> +    set instruction_position(11) 1

> +    set instruction_position(12) 2

> +    set instruction_position(13) 1

> +}

> +

>  if ![runto_main] {

>      untested "failed to run to main"

>      return -1

> @@ -56,10 +114,11 @@ if ![runto_main] {

>  global gdb_prompt

>  

>  proc check_replay_at { insn } {

> +  global instructions_count

>    gdb_test "info record" [multi_line \

>      "Active record target: record-btrace" \

>      ".*" \

> -    "Recorded 40 instructions in 16 functions \\\(0 gaps\\\) for .*" \

> +    "Recorded $instructions_count instructions in 16 functions \\\(0 gaps\\\) for .*" \

>      "Replay in progress\.  At instruction $insn\." \

>      ] "check replay at $insn"

>  }

> @@ -74,15 +133,14 @@ with_test_prefix "record" {

>  with_test_prefix "fetch" {

>      gdb_test "reverse-stepi" ".*fun4\.5.*" "reverse-stepi.1"

>      gdb_test "reverse-stepi" ".*fun4\.5.*" "reverse-stepi.2"

> -

>      # let's check where we are in the trace

> -    check_replay_at 39

> +    check_replay_at $instruction_position(0) 

>  }

>  

>  # let's step forward and check again

>  with_test_prefix "stepi" {

>      gdb_test "stepi" ".*fun4\.5.*"

> -    check_replay_at 40

> +    check_replay_at $instruction_position(1) 

>  }

>  

>  # with the next step, we stop replaying

> @@ -91,14 +149,17 @@ with_test_prefix "end" {

>      gdb_test "info record" [multi_line \

>        "Active record target: record-btrace" \

>        ".*" \

> -      "Recorded 40 instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \

> +      "Recorded $instructions_count instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \

>    ] 

>  }

>  

> +#recover from a missing lr register in arm

> +gdb_test "record goto end"

> +

>  # let's try nexti

>  with_test_prefix "reverse-nexti.1" {

>      gdb_test "reverse-nexti" ".*main\.2.*"

> -    check_replay_at 1

> +    check_replay_at $instruction_position(2)

>  }

>  

>  # we can't reverse-nexti any further

> @@ -106,7 +167,7 @@ with_test_prefix "reverse-nexti.2" {

>      gdb_test "reverse-nexti" \

>  	"No more reverse-execution history\.\r\n.*main\.2.*" \

>  	"reverse-nexti.2"

> -    check_replay_at 1

> +    check_replay_at $instruction_position(3)

>  }

>  

>  # but we can step back again

> @@ -115,32 +176,32 @@ with_test_prefix "nexti" {

>      gdb_test "info record" [multi_line \

>        "Active record target: record-btrace" \

>        ".*" \

> -      "Recorded 40 instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \

> +      "Recorded $instructions_count instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \

>  			       ]

>  }

>  

>  # let's step from a goto position somewhere in the middle

>  with_test_prefix "goto" {

> -    gdb_test "record goto 22" ".*fun3\.2.*"

> -    with_test_prefix "goto 22" { check_replay_at 22 }

> +    gdb_test "record goto $instruction_position(4) " ".*fun3\.2.*"

> +    with_test_prefix "goto $instruction_position(4) " { check_replay_at $instruction_position(4)  }

>  

>      gdb_test "stepi" ".*fun1\.1.*" "stepi.3"

> -    with_test_prefix "stepi to 23" { check_replay_at 23 }

> +    with_test_prefix "stepi to $instruction_position(5)" { check_replay_at $instruction_position(5) }

>  

>      gdb_test "reverse-stepi" ".*fun3\.2.*" "reverse-stepi.3"

> -    with_test_prefix "reverse-stepi to 22" { check_replay_at 22 }

> +    with_test_prefix "reverse-stepi to $instruction_position(6)" { check_replay_at $instruction_position(6) }

>  

>      gdb_test "nexti" ".*fun3\.3.*"

> -    with_test_prefix "nexti to 27" { check_replay_at 27 }

> +    with_test_prefix "nexti to $instruction_position(7) " { check_replay_at $instruction_position(7)  }

>  

>      gdb_test "reverse-nexti" ".*fun3\.2.*" "reverse-nexti.3"

> -    with_test_prefix "reverse-nexti to 22" { check_replay_at 22 }

> +    with_test_prefix "reverse-nexti to $instruction_position(8)" { check_replay_at $instruction_position(8) }

>  }

>  

>  # let's try to step off the left end

>  with_test_prefix "goto begin" {

>      gdb_test "record goto begin" ".*main\.2.*"

> -    check_replay_at 1

> +    check_replay_at $instruction_position(9)

>  

>      with_test_prefix "reverse-stepi" {

>  	gdb_test "reverse-stepi" \

> @@ -149,7 +210,7 @@ with_test_prefix "goto begin" {

>  	gdb_test "reverse-stepi" \

>  	    "No more reverse-execution history\.\r\n.*main\.2.*" \

>  	    "reverse-stepi.2"

> -	check_replay_at 1

> +	check_replay_at $instruction_position(10)

>      }

>  

>      with_test_prefix "reverse-nexti" {

> @@ -159,13 +220,13 @@ with_test_prefix "goto begin" {

>  	gdb_test "reverse-nexti" \

>  	    "No more reverse-execution history\.\r\n.*main\.2.*" \

>  	    "reverse-nexti.2"

> -	check_replay_at 1

> +	check_replay_at $instruction_position(11)

>      }

>  

>      # we can step forward, though

>      with_test_prefix "stepi" {

>  	gdb_test "stepi" ".*fun4\.1.*"

> -	check_replay_at 2

> +	check_replay_at $instruction_position(12)

>      }

>  }

>  

> @@ -178,5 +239,5 @@ with_test_prefix "reverse-stepi" {

>      gdb_test "reverse-stepi" \

>  	"No more reverse-execution history\.\r\n.*main\.2.*" \

>  	"reverse-stepi.3"

> -    check_replay_at 1

> +    check_replay_at $instruction_position(13)

>  }

> diff --git a/gdb/testsuite/gdb.btrace/tailcall-only.exp b/gdb/testsuite/gdb.btrace/tailcall-only.exp

> index 510f90c9d5e..036da4a2020 100644

> --- a/gdb/testsuite/gdb.btrace/tailcall-only.exp

> +++ b/gdb/testsuite/gdb.btrace/tailcall-only.exp

> @@ -37,15 +37,23 @@ if [info exists COMPILE] {

>      # make check RUNTESTFLAGS="gdb.btrace/tailcall-only.exp COMPILE=1"

>      standard_testfile tailcall-only.c

>      lappend opts debug optimize=-O2

> -} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +} else {

> +  set test_prefix ""

> +  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>      if {[is_amd64_regs_target]} {

> -		standard_testfile x86_64-tailcall-only.S

> +      set test_prefix "x86_64"

>      } else {

> -		standard_testfile i686-tailcall-only.S

> +      set test_prefix "i686"

>      }

> -} else {

> +  } elseif {[istarget "arm*-*-*"]} {

> +      set test_prefix "arm"

> +  } elseif {[istarget "aarch64*-*-*"]} {

> +    set test_prefix "aarch64"

> +  } else {

>      unsupported "target architecture not supported"

>      return -1

> +  }

> +  standard_testfile $test_prefix-tailcall-only.S

>  }

>  

>  if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {

> @@ -62,6 +70,10 @@ gdb_test_no_output "set record function-call-history-size 0"

>  

>  # trace foo

>  gdb_test "step" ".*" "prepare for recording"

> +# make sure we get out of function epilogue

> +if { [istarget "arm*-*-*"] } {

> +  gdb_test "stepi"

> +}

>  gdb_test_no_output "record btrace"

>  gdb_test "stepi 4" ".*" "record branch trace"

>  

> diff --git a/gdb/testsuite/gdb.btrace/tailcall.exp b/gdb/testsuite/gdb.btrace/tailcall.exp

> index 07a3ec103f4..70fda8a5670 100644

> --- a/gdb/testsuite/gdb.btrace/tailcall.exp

> +++ b/gdb/testsuite/gdb.btrace/tailcall.exp

> @@ -34,20 +34,42 @@ if [info exists COMPILE] {

>      # make check RUNTESTFLAGS="gdb.btrace/tailcall.exp COMPILE=1"

>      standard_testfile tailcall.c

>      lappend opts debug optimize=-O2

> -} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +} else {

> +  set test_prefix ""

> +  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>      if {[is_amd64_regs_target]} {

> -		standard_testfile x86_64-tailcall.S

> +      set test_prefix "x86_64"

>      } else {

> -		standard_testfile i686-tailcall.S

> +      set test_prefix "i686"

>      }

> -} else {

> +  } elseif {[istarget "arm*-*-*"]} {

> +      set test_prefix "arm"

> +  } elseif {[istarget "aarch64*-*-*"]} {

> +    set test_prefix "aarch64"

> +  } else {

>      unsupported "target architecture not supported"

>      return -1

> +  }

> +  standard_testfile $test_prefix-tailcall.S

>  }

>  

>  if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {

>      return -1

>  }

> +

> +if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    set bar_return_line 24

> +    set bar_return_position 4

> +    set main_return_line 38

> +} elseif {[istarget "arm*-*-*"]} {

> +    set bar_return_line 24

> +    set bar_return_position 5

> +    set main_return_line 41

> +    } elseif {[istarget "aarch64*-*-*"]} {

> +    set bar_return_line 23

> +    set bar_return_position 6

> +    set main_return_line 40

> +}

>  if ![runto_main] {

>      untested "failed to run to main"

>      return -1

> @@ -58,7 +80,17 @@ gdb_test_no_output "set record function-call-history-size 0"

>  

>  # trace the call to foo

>  gdb_test_no_output "record btrace"

> -gdb_test "next 2"

> +

> +# make sure we get out of function epilogue

> +if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

> +    gdb_test "next 2"

> +} elseif {[istarget "arm*-*-*"]} {

> +  gdb_test "next 2"

> +  gdb_test "stepi"

> +} elseif {[istarget "aarch64*-*-*"]} {

> +  gdb_test "next"

> +  gdb_test "stepi 2"

> +}

>  

>  # show the flat branch trace

>  gdb_test "record function-call-history 1" [multi_line \

> @@ -77,11 +109,11 @@ gdb_test "record function-call-history /c 1" [multi_line \

>    ] "indented"

>  

>  # go into bar

> -gdb_test "record goto 4" ".*bar \\(\\) at .*tailcall.c:24\r\n.*"

> +gdb_test "record goto $bar_return_position" ".*bar \\(\\) at .*tailcall.c:$bar_return_line\r\n.*"

>  

>  # check the backtrace

>  gdb_test "backtrace" [multi_line \

> -  "#0.*bar \\(\\) at tailcall.c:24" \

> +  "#0.*bar \\(\\) at tailcall.c:$bar_return_line" \

>    "#1.*foo \\(\\) at tailcall.c:29" \

>    "#2.*main \\(\\) at tailcall.c:37" \

>    "Backtrace stopped: not enough registers or memory available to unwind further" \

> @@ -93,23 +125,23 @@ gdb_test "up" "#2\[^\r\n\]*main \\(\\) at tailcall.c:37\r\n.*" "up to main"

>  gdb_test "down" "#1\[^\r\n\]*foo \\(\\) at tailcall.c:29\r\n.*" "down to foo"

>  

>  # test stepping into and out of tailcalls.

> -gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:38\r\n.*" \

> +gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:$main_return_line\r\n.*" \

>      "finish.1"

> -gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:24\r\n.*" \

> +gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:$bar_return_line\r\n.*" \

>      "reverse-step.1"

>  gdb_test "reverse-finish" "\[^\r\n\]*foo \\(\\) at tailcall.c:29\r\n.*" \

>      "reverse-finish.1"

>  gdb_test "reverse-step" "\[^\r\n\]*main \\(\\) at tailcall.c:37\r\n.*" \

>      "reverse-step.2"

> -gdb_test "next" "\[^\r\n\]*38.*" \

> +gdb_test "next" "\[^\r\n\]*$main_return_line.*" \

>      "next.1"

>  gdb_test "reverse-next" "\[^\r\n\]*main \\(\\) at tailcall.c:37\r\n.*" \

>      "reverse-next.1"

>  gdb_test "step" "\[^\r\n\]*foo \\(\\) at tailcall.c:29\r\n.*" \

>      "step.1"

> -gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:38\r\n.*" \

> +gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:$main_return_line\r\n.*" \

>      "finish.2"

> -gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:24\r\n.*" \

> +gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:$bar_return_line\r\n.*" \

>      "reverse-step.3"

> -gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:38\r\n.*" \

> +gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:$main_return_line\r\n.*" \

>      "finish.3"

> diff --git a/gdb/testsuite/gdb.btrace/instruction_history.S b/gdb/testsuite/gdb.btrace/x86-instruction_history.S

> similarity index 100%

> rename from gdb/testsuite/gdb.btrace/instruction_history.S

> rename to gdb/testsuite/gdb.btrace/x86-instruction_history.S

> diff --git a/gdb/testsuite/lib/gdb.exp b/gdb/testsuite/lib/gdb.exp

> index 36a5fd4feb7..02cf8a3cec6 100644

> --- a/gdb/testsuite/lib/gdb.exp

> +++ b/gdb/testsuite/lib/gdb.exp

> @@ -3248,7 +3248,7 @@ gdb_caching_proc skip_btrace_tests {

>      global srcdir subdir gdb_prompt inferior_exited_re

>  

>      set me "skip_btrace_tests"

> -    if { ![istarget "i?86-*-*"] && ![istarget "x86_64-*-*"] } {

> +    if { ![istarget "i?86-*-*"] && ![istarget "x86_64-*-*"] && ![istarget "arm*-*-*"] && ![istarget "aarch64*-*-*"]} {

>          verbose "$me:  target does not support btrace, returning 1" 2

>          return 1

>      }

> -- 

> 2.25.1

>
Weimin Pan via Gdb-patches June 23, 2021, 2:16 p.m. | #2
Hello Zied,

>+   This file has been generated on an armv8 machine using:

>+   gcc -m32 -S -O2 -dA -g tailcall-only.c -o aarch64-tailcall-only.S


Does the aarch64- prefix still hold when compiled with -m32?


>diff --git a/gdb/testsuite/gdb.btrace/buffer-size.exp

>b/gdb/testsuite/gdb.btrace/buffer-size.exp

>index ea4e36c1593..23f859dce9c 100644

>--- a/gdb/testsuite/gdb.btrace/buffer-size.exp

>+++ b/gdb/testsuite/gdb.btrace/buffer-size.exp

>@@ -32,10 +32,17 @@ if ![runto_main] {

>     return -1

> }

>

>-gdb_test_no_output "set record btrace bts buffer-size 1"

>-gdb_test_no_output "set record btrace pt buffer-size 1"

>-gdb_test "show record btrace bts buffer-size" "The record/replay bts buffer size

>is 1\.\r"

>-gdb_test "show record btrace pt buffer-size" "The record/replay pt buffer size is

>1\.\r"

>+set btrace_type ""

>+if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>+    set btrace_type { "bts" "pt" }

>+} elseif {[istarget "arm*-*-*"]|| [istarget "aarch64*-*-*"]} {

>+    set btrace_type { "etm" }

>+}


There shouldn't be a need for this.  The config should work for all formats, even
if the target does not support it.  We should be able to run the below loop over
all existing formats.


>diff --git a/gdb/testsuite/gdb.btrace/instruction_history.exp

>b/gdb/testsuite/gdb.btrace/instruction_history.exp

>index 403085c083f..3a6e7362f74 100644

>--- a/gdb/testsuite/gdb.btrace/instruction_history.exp

>+++ b/gdb/testsuite/gdb.btrace/instruction_history.exp

>@@ -22,7 +22,17 @@ if { [skip_btrace_tests] } {

>     return -1

> }

>

>-standard_testfile .c .S

>+set test_prefix ""

>+if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>+    set test_prefix "x86"

>+} elseif {[istarget "arm*-*-*"]} {

>+    set test_prefix "arm"

>+} elseif {[istarget "aarch64*-*-*"]} {

>+    set test_prefix "aarch64"

>+}


We should error out to give a more meaningful error message in case
we cannot determine the prefix.


>diff --git a/gdb/testsuite/gdb.btrace/non-stop.exp

>b/gdb/testsuite/gdb.btrace/non-stop.exp

>index e509d65d660..fbc4cda7dd6 100644

>--- a/gdb/testsuite/gdb.btrace/non-stop.exp

>+++ b/gdb/testsuite/gdb.btrace/non-stop.exp

>@@ -31,6 +31,12 @@ save_vars { GDBFLAGS } {

>     clean_restart $testfile

> }

>

>+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>+    set loop_position 2

>+} elseif {[istarget "arm*-*-*"] || [istarget "aarch64*-*-*"]} {

>+    set loop_position 3

>+}

>+

> if ![runto_main] {

>     untested "failed to run to main"

>     return -1

>@@ -111,87 +117,99 @@ gdb_test "thread apply all info rec" ".*"

> gdb_test "info threads" ".*"

>

> with_test_prefix "navigate" {

>-    gdb_test "thread apply 1 record goto 3" "$loop_line"

>-    gdb_test "thread apply 2 record goto 4" "$loop_line"

>+    gdb_test "thread apply 1 record goto [expr {$loop_position + 1}]"

>"$loop_line"

>+    gdb_test "thread apply 2 record goto [expr {$loop_position + 2}]"

>"$loop_line"


This test is already making assumptions about the compiled code.

I'd rather we started at 4 for all architectures instead of having different
starting points.  We may also adjust the tests so we don't go beyond 12,
which seems to be working for all IA targets we're running this on.  We
can also try to stay below 10 to be on the safe side.

Could you propose something that works for ARM in v7 of the series?
I can validate that on IA, then, before this gets merged.  If we stay between
3 and 12, however, I don't see why it shouldn't continue working.


>+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>+    set function_positions(0) 19

>+    set function_positions(1) 27

>+    set function_positions(2) 2

>+    set function_positions(end) 40

>+    set function_positions(3) 39

>+

>+    set sequence_begin(1) 1

>+    set sequence_end(1) 1

>+    set sequence_begin(2) 2

>+    set sequence_end(2) 4


That's too cryptic.  If we cannot tweak the assembly files to work
with the same .exp, I'd rather split the latter into arch-specific .exp's.

Also for other tests below.


> if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {

>@@ -62,6 +70,10 @@ gdb_test_no_output "set record function-call-history-size

>0"

>

> # trace foo

> gdb_test "step" ".*" "prepare for recording"

>+# make sure we get out of function epilogue

>+if { [istarget "arm*-*-*"] } {

>+  gdb_test "stepi"

>+}


We can also work with breakpoints if stepping isn't producing reliable
results.


>     lappend opts debug optimize=-O2

>-} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>+} else {

>+  set test_prefix ""

>+  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {


Extra space between { and [.  Let's be consistent in formatting.


> if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {

>     return -1

> }

>+

>+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {

>+    set bar_return_line 24

>+    set bar_return_position 4

>+    set main_return_line 38

>+} elseif {[istarget "arm*-*-*"]} {

>+    set bar_return_line 24

>+    set bar_return_position 5

>+    set main_return_line 41

>+    } elseif {[istarget "aarch64*-*-*"]} {

>+    set bar_return_line 23

>+    set bar_return_position 6

>+    set main_return_line 40

>+}


Why would compilers not agree on the source line of the return statement?

I can see that the "record goto 4" is causing trouble.  Can we just tweak that
number?  I.e. find another place inside the trace that produces the same bt?

We can also try to work with breakpoints again, instead of hard-coding an
instruction number.

Regards,
Markus.
Intel Deutschland GmbH
Registered Address: Am Campeon 10, 85579 Neubiberg, Germany
Tel: +49 89 99 8853-0, www.intel.de <http://www.intel.de>
Managing Directors: Christin Eisenschmid, Sharon Heck, Tiffany Doon Silva  
Chairperson of the Supervisory Board: Nicole Lau
Registered Office: Munich
Commercial Register: Amtsgericht Muenchen HRB 186928

Patch

diff --git a/gdb/testsuite/gdb.btrace/aarch64-instruction_history.S b/gdb/testsuite/gdb.btrace/aarch64-instruction_history.S
new file mode 100644
index 00000000000..0ccf43a1cf4
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/aarch64-instruction_history.S
@@ -0,0 +1,31 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.  */
+.arch armv8-a
+.text
+.globl loop
+.type  loop, %function
+loop:
+	mov x0, #2 /* bp.1 */
+L1:
+	cmp x0, #0
+	beq L2
+	subs x0, x0, #1
+	b L1
+L2:
+	ret /* bp.2 */
+
+
diff --git a/gdb/testsuite/gdb.btrace/aarch64-record_goto.S b/gdb/testsuite/gdb.btrace/aarch64-record_goto.S
new file mode 100644
index 00000000000..282f8d41a3c
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/aarch64-record_goto.S
@@ -0,0 +1,399 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.
+
+   This file has been generated on an armv8 machine using:
+   gcc -S -dA -g record_goto.c -o aarch64-record_goto.S  */
+
+	.arch armv8-a
+	.file	"record_goto.c"
+	.text
+.Ltext0:
+	.align	2
+	.global	fun1
+	//.tune generic
+	.type	fun1, %function
+fun1:
+.LFB0:
+	.file 1 "record_goto.c"
+	// record_goto.c:22:1
+	.loc 1 22 1
+	.cfi_startproc
+// BLOCK 2 seq:0
+// PRED: ENTRY (FALLTHRU)
+	// record_goto.c:23:1
+	.loc 1 23 1
+	nop
+// SUCC: EXIT [always] 
+	ret
+	.cfi_endproc
+.LFE0:
+	.size	fun1, .-fun1
+	.align	2
+	.global	fun2
+	.type	fun2, %function
+fun2:
+.LFB1:
+	// record_goto.c:27:1
+	.loc 1 27 1
+	.cfi_startproc
+// BLOCK 2 seq:0
+// PRED: ENTRY (FALLTHRU)
+	stp	x29, x30, [sp, -16]!
+	.cfi_def_cfa_offset 16
+	.cfi_offset 29, -16
+	.cfi_offset 30, -8
+	mov	x29, sp
+	// record_goto.c:28:3
+	.loc 1 28 3
+	bl	fun1
+	// record_goto.c:29:1
+	.loc 1 29 1
+	nop
+	ldp	x29, x30, [sp], 16
+	.cfi_restore 30
+	.cfi_restore 29
+	.cfi_def_cfa_offset 0
+// SUCC: EXIT [always] 
+	ret
+	.cfi_endproc
+.LFE1:
+	.size	fun2, .-fun2
+	.align	2
+	.global	fun3
+	.type	fun3, %function
+fun3:
+.LFB2:
+	// record_goto.c:33:1
+	.loc 1 33 1
+	.cfi_startproc
+// BLOCK 2 seq:0
+// PRED: ENTRY (FALLTHRU)
+	stp	x29, x30, [sp, -16]!
+	.cfi_def_cfa_offset 16
+	.cfi_offset 29, -16
+	.cfi_offset 30, -8
+	mov	x29, sp
+	// record_goto.c:34:3
+	.loc 1 34 3
+	bl	fun1
+	// record_goto.c:35:3
+	.loc 1 35 3
+	bl	fun2
+	// record_goto.c:36:1
+	.loc 1 36 1
+	nop
+	ldp	x29, x30, [sp], 16
+	.cfi_restore 30
+	.cfi_restore 29
+	.cfi_def_cfa_offset 0
+// SUCC: EXIT [always] 
+	ret
+	.cfi_endproc
+.LFE2:
+	.size	fun3, .-fun3
+	.align	2
+	.global	fun4
+	.type	fun4, %function
+fun4:
+.LFB3:
+	// record_goto.c:40:1
+	.loc 1 40 1
+	.cfi_startproc
+// BLOCK 2 seq:0
+// PRED: ENTRY (FALLTHRU)
+	stp	x29, x30, [sp, -16]!
+	.cfi_def_cfa_offset 16
+	.cfi_offset 29, -16
+	.cfi_offset 30, -8
+	mov	x29, sp
+	// record_goto.c:41:3
+	.loc 1 41 3
+	bl	fun1
+	// record_goto.c:42:3
+	.loc 1 42 3
+	bl	fun2
+	// record_goto.c:43:3
+	.loc 1 43 3
+	bl	fun3
+	// record_goto.c:44:1
+	.loc 1 44 1
+	nop
+	ldp	x29, x30, [sp], 16
+	.cfi_restore 30
+	.cfi_restore 29
+	.cfi_def_cfa_offset 0
+// SUCC: EXIT [always] 
+	ret
+	.cfi_endproc
+.LFE3:
+	.size	fun4, .-fun4
+	.align	2
+	.global	main
+	.type	main, %function
+main:
+.LFB4:
+	// record_goto.c:48:1
+	.loc 1 48 1
+	.cfi_startproc
+// BLOCK 2 seq:0
+// PRED: ENTRY (FALLTHRU)
+	stp	x29, x30, [sp, -16]!
+	.cfi_def_cfa_offset 16
+	.cfi_offset 29, -16
+	.cfi_offset 30, -8
+	mov	x29, sp
+	// record_goto.c:49:3
+	.loc 1 49 3
+	bl	fun4
+	// record_goto.c:50:10
+	.loc 1 50 10
+	mov	w0, 0
+	// record_goto.c:51:1
+	.loc 1 51 1
+	ldp	x29, x30, [sp], 16
+	.cfi_restore 30
+	.cfi_restore 29
+	.cfi_def_cfa_offset 0
+// SUCC: EXIT [always] 
+	ret
+	.cfi_endproc
+.LFE4:
+	.size	main, .-main
+.Letext0:
+	.section	.debug_info,"",@progbits
+.Ldebug_info0:
+	.4byte	0xb7	// Length of Compilation Unit Info
+	.2byte	0x4	// DWARF version number
+	.4byte	.Ldebug_abbrev0	// Offset Into Abbrev. Section
+	.byte	0x8	// Pointer Size (in bytes)
+	.uleb128 0x1	// (DIE (0xb) DW_TAG_compile_unit)
+	.4byte	.LASF4	// DW_AT_producer: "GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -fasynchronous-unwind-tables"
+	.byte	0xc	// DW_AT_language
+	.4byte	.LASF5	// DW_AT_name: "record_goto.c"
+	.4byte	.LASF6	// DW_AT_comp_dir: "/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+	.8byte	.Ltext0	// DW_AT_low_pc
+	.8byte	.Letext0-.Ltext0	// DW_AT_high_pc
+	.4byte	.Ldebug_line0	// DW_AT_stmt_list
+	.uleb128 0x2	// (DIE (0x2d) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF7	// DW_AT_name: "main"
+	.byte	0x1	// DW_AT_decl_file (record_goto.c)
+	.byte	0x2f	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x4b	// DW_AT_type
+	.8byte	.LFB4	// DW_AT_low_pc
+	.8byte	.LFE4-.LFB4	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x3	// (DIE (0x4b) DW_TAG_base_type)
+	.byte	0x4	// DW_AT_byte_size
+	.byte	0x5	// DW_AT_encoding
+	.ascii "int\0"	// DW_AT_name
+	.uleb128 0x4	// (DIE (0x52) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF0	// DW_AT_name: "fun4"
+	.byte	0x1	// DW_AT_decl_file (record_goto.c)
+	.byte	0x27	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.8byte	.LFB3	// DW_AT_low_pc
+	.8byte	.LFE3-.LFB3	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x4	// (DIE (0x6c) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF1	// DW_AT_name: "fun3"
+	.byte	0x1	// DW_AT_decl_file (record_goto.c)
+	.byte	0x20	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.8byte	.LFB2	// DW_AT_low_pc
+	.8byte	.LFE2-.LFB2	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x4	// (DIE (0x86) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF2	// DW_AT_name: "fun2"
+	.byte	0x1	// DW_AT_decl_file (record_goto.c)
+	.byte	0x1a	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.8byte	.LFB1	// DW_AT_low_pc
+	.8byte	.LFE1-.LFB1	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x5	// (DIE (0xa0) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF3	// DW_AT_name: "fun1"
+	.byte	0x1	// DW_AT_decl_file (record_goto.c)
+	.byte	0x15	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.8byte	.LFB0	// DW_AT_low_pc
+	.8byte	.LFE0-.LFB0	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.byte	0	// end of children of DIE 0xb
+	.section	.debug_abbrev,"",@progbits
+.Ldebug_abbrev0:
+	.uleb128 0x1	// (abbrev code)
+	.uleb128 0x11	// (TAG: DW_TAG_compile_unit)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x25	// (DW_AT_producer)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x13	// (DW_AT_language)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x1b	// (DW_AT_comp_dir)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x10	// (DW_AT_stmt_list)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x2	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0	// DW_children_no
+	.uleb128 0x3f	// (DW_AT_external)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2116	// (DW_AT_GNU_all_tail_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.uleb128 0x3	// (abbrev code)
+	.uleb128 0x24	// (TAG: DW_TAG_base_type)
+	.byte	0	// DW_children_no
+	.uleb128 0xb	// (DW_AT_byte_size)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3e	// (DW_AT_encoding)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0x8	// (DW_FORM_string)
+	.byte	0
+	.byte	0
+	.uleb128 0x4	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0	// DW_children_no
+	.uleb128 0x3f	// (DW_AT_external)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2116	// (DW_AT_GNU_all_tail_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.uleb128 0x5	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0	// DW_children_no
+	.uleb128 0x3f	// (DW_AT_external)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.byte	0
+	.section	.debug_aranges,"",@progbits
+	.4byte	0x2c	// Length of Address Ranges Info
+	.2byte	0x2	// DWARF aranges version
+	.4byte	.Ldebug_info0	// Offset of Compilation Unit Info
+	.byte	0x8	// Size of Address
+	.byte	0	// Size of Segment Descriptor
+	.2byte	0	// Pad to 16 byte boundary
+	.2byte	0
+	.8byte	.Ltext0	// Address
+	.8byte	.Letext0-.Ltext0	// Length
+	.8byte	0
+	.8byte	0
+	.section	.debug_line,"",@progbits
+.Ldebug_line0:
+	.section	.debug_str,"MS",@progbits,1
+.LASF5:
+	.string	"record_goto.c"
+.LASF4:
+	.string	"GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -fasynchronous-unwind-tables"
+.LASF3:
+	.string	"fun1"
+.LASF2:
+	.string	"fun2"
+.LASF0:
+	.string	"fun4"
+.LASF6:
+	.string	"/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+.LASF7:
+	.string	"main"
+.LASF1:
+	.string	"fun3"
+	.ident	"GCC: (Debian 10.2.1-3) 10.2.1 20201224"
+	.section	.note.GNU-stack,"",@progbits
diff --git a/gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S b/gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S
new file mode 100644
index 00000000000..f3e12ef2bc8
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/aarch64-tailcall-only.S
@@ -0,0 +1,516 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.
+
+   This file has been generated on an armv8 machine using:
+   gcc -m32 -S -O2 -dA -g tailcall-only.c -o aarch64-tailcall-only.S
+ */
+
+	.arch armv8-a
+	.file	"tailcall-only.c"
+	.text
+.Ltext0:
+	.align	2
+	.p2align 4,,11
+	//.tune generic
+	.type	bar_1, %function
+bar_1:
+.LFB0:
+	.file 1 "tailcall-only.c"
+	// tailcall-only.c:22:1
+	.loc 1 22 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall-only.c:23:3
+	.loc 1 23 3 view .LVU1
+	// tailcall-only.c:24:1
+	.loc 1 24 1 is_stmt 0 view .LVU2
+	mov	w0, 42
+// SUCC: EXIT [always]  count:1073741824 (estimated locally)
+	ret
+	.cfi_endproc
+.LFE0:
+	.size	bar_1, .-bar_1
+	.align	2
+	.p2align 4,,11
+	.type	bar, %function
+bar:
+.LFB1:
+	// tailcall-only.c:28:1
+	.loc 1 28 1 is_stmt 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall-only.c:29:3
+	.loc 1 29 3 view .LVU4
+// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)
+	// tailcall-only.c:29:10
+	.loc 1 29 10 is_stmt 0 view .LVU5
+	b	bar_1
+.LVL0:
+	.cfi_endproc
+.LFE1:
+	.size	bar, .-bar
+	.align	2
+	.p2align 4,,11
+	.type	foo_1, %function
+foo_1:
+.LFB2:
+	// tailcall-only.c:34:1
+	.loc 1 34 1 is_stmt 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall-only.c:35:3
+	.loc 1 35 3 view .LVU7
+// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)
+	// tailcall-only.c:35:10
+	.loc 1 35 10 is_stmt 0 view .LVU8
+	b	bar
+.LVL1:
+	.cfi_endproc
+.LFE2:
+	.size	foo_1, .-foo_1
+	.align	2
+	.p2align 4,,11
+	.type	foo, %function
+foo:
+.LFB3:
+	// tailcall-only.c:40:1
+	.loc 1 40 1 is_stmt 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall-only.c:41:3
+	.loc 1 41 3 view .LVU10
+// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)
+	// tailcall-only.c:41:10
+	.loc 1 41 10 is_stmt 0 view .LVU11
+	b	foo_1
+.LVL2:
+	.cfi_endproc
+.LFE3:
+	.size	foo, .-foo
+	.section	.text.startup,"ax",@progbits
+	.align	2
+	.p2align 4,,11
+	.global	main
+	.type	main, %function
+main:
+.LFB4:
+	// tailcall-only.c:46:1
+	.loc 1 46 1 is_stmt 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall-only.c:47:3
+	.loc 1 47 3 view .LVU13
+	// tailcall-only.c:49:3
+	.loc 1 49 3 view .LVU14
+	// tailcall-only.c:46:1
+	.loc 1 46 1 is_stmt 0 view .LVU15
+	stp	x29, x30, [sp, -16]!
+	.cfi_def_cfa_offset 16
+	.cfi_offset 29, -16
+	.cfi_offset 30, -8
+	mov	x29, sp
+	// tailcall-only.c:49:12
+	.loc 1 49 12 view .LVU16
+	bl	foo
+.LVL3:
+	// DEBUG answer => x0
+	// tailcall-only.c:50:3
+	.loc 1 50 3 is_stmt 1 view .LVU17
+	// DEBUG answer => x0+0x1
+	// tailcall-only.c:52:3
+	.loc 1 52 3 view .LVU18
+	// tailcall-only.c:53:1
+	.loc 1 53 1 is_stmt 0 view .LVU19
+	add	w0, w0, 1
+.LVL4:
+	// DEBUG answer => x0
+	// tailcall-only.c:53:1
+	.loc 1 53 1 view .LVU20
+	ldp	x29, x30, [sp], 16
+	.cfi_restore 30
+	.cfi_restore 29
+	.cfi_def_cfa_offset 0
+// SUCC: EXIT [always]  count:1073741824 (estimated locally)
+	ret
+	.cfi_endproc
+.LFE4:
+	.size	main, .-main
+	.text
+.Letext0:
+	.section	.debug_info,"",@progbits
+.Ldebug_info0:
+	.4byte	0x11f	// Length of Compilation Unit Info
+	.2byte	0x4	// DWARF version number
+	.4byte	.Ldebug_abbrev0	// Offset Into Abbrev. Section
+	.byte	0x8	// Pointer Size (in bytes)
+	.uleb128 0x1	// (DIE (0xb) DW_TAG_compile_unit)
+	.4byte	.LASF1	// DW_AT_producer: "GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"
+	.byte	0xc	// DW_AT_language
+	.4byte	.LASF2	// DW_AT_name: "tailcall-only.c"
+	.4byte	.LASF3	// DW_AT_comp_dir: "/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+	.4byte	.Ldebug_ranges0+0	// DW_AT_ranges
+	.8byte	0	// DW_AT_low_pc
+	.4byte	.Ldebug_line0	// DW_AT_stmt_list
+	.uleb128 0x2	// (DIE (0x29) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF4	// DW_AT_name: "main"
+	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)
+	.byte	0x2d	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB4	// DW_AT_low_pc
+	.8byte	.LFE4-.LFB4	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.4byte	0x6d	// DW_AT_sibling
+	.uleb128 0x3	// (DIE (0x4b) DW_TAG_variable)
+	.4byte	.LASF5	// DW_AT_name: "answer"
+	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)
+	.byte	0x2f	// DW_AT_decl_line
+	.byte	0x7	// DW_AT_decl_column
+	.4byte	0x6d	// DW_AT_type
+	.4byte	.LLST0	// DW_AT_location
+	.4byte	.LVUS0	// DW_AT_GNU_locviews
+	.uleb128 0x4	// (DIE (0x5f) DW_TAG_GNU_call_site)
+	.8byte	.LVL3	// DW_AT_low_pc
+	.4byte	0x74	// DW_AT_abstract_origin
+	.byte	0	// end of children of DIE 0x29
+	.uleb128 0x5	// (DIE (0x6d) DW_TAG_base_type)
+	.byte	0x4	// DW_AT_byte_size
+	.byte	0x5	// DW_AT_encoding
+	.ascii "int\0"	// DW_AT_name
+	.uleb128 0x6	// (DIE (0x74) DW_TAG_subprogram)
+	.ascii "foo\0"	// DW_AT_name
+	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)
+	.byte	0x27	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB3	// DW_AT_low_pc
+	.8byte	.LFE3-.LFB3	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.4byte	0xa4	// DW_AT_sibling
+	.uleb128 0x7	// (DIE (0x96) DW_TAG_GNU_call_site)
+	.8byte	.LVL2	// DW_AT_low_pc
+			// DW_AT_GNU_tail_call
+	.4byte	0xa4	// DW_AT_abstract_origin
+	.byte	0	// end of children of DIE 0x74
+	.uleb128 0x8	// (DIE (0xa4) DW_TAG_subprogram)
+	.4byte	.LASF0	// DW_AT_name: "foo_1"
+	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)
+	.byte	0x21	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB2	// DW_AT_low_pc
+	.8byte	.LFE2-.LFB2	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.4byte	0xd4	// DW_AT_sibling
+	.uleb128 0x7	// (DIE (0xc6) DW_TAG_GNU_call_site)
+	.8byte	.LVL1	// DW_AT_low_pc
+			// DW_AT_GNU_tail_call
+	.4byte	0xd4	// DW_AT_abstract_origin
+	.byte	0	// end of children of DIE 0xa4
+	.uleb128 0x6	// (DIE (0xd4) DW_TAG_subprogram)
+	.ascii "bar\0"	// DW_AT_name
+	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)
+	.byte	0x1b	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB1	// DW_AT_low_pc
+	.8byte	.LFE1-.LFB1	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.4byte	0x104	// DW_AT_sibling
+	.uleb128 0x7	// (DIE (0xf6) DW_TAG_GNU_call_site)
+	.8byte	.LVL0	// DW_AT_low_pc
+			// DW_AT_GNU_tail_call
+	.4byte	0x104	// DW_AT_abstract_origin
+	.byte	0	// end of children of DIE 0xd4
+	.uleb128 0x9	// (DIE (0x104) DW_TAG_subprogram)
+	.4byte	.LASF6	// DW_AT_name: "bar_1"
+	.byte	0x1	// DW_AT_decl_file (tailcall-only.c)
+	.byte	0x15	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB0	// DW_AT_low_pc
+	.8byte	.LFE0-.LFB0	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.byte	0	// end of children of DIE 0xb
+	.section	.debug_abbrev,"",@progbits
+.Ldebug_abbrev0:
+	.uleb128 0x1	// (abbrev code)
+	.uleb128 0x11	// (TAG: DW_TAG_compile_unit)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x25	// (DW_AT_producer)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x13	// (DW_AT_language)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x1b	// (DW_AT_comp_dir)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x55	// (DW_AT_ranges)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x10	// (DW_AT_stmt_list)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x2	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x3f	// (DW_AT_external)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x1	// (DW_AT_sibling)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x3	// (abbrev code)
+	.uleb128 0x34	// (TAG: DW_TAG_variable)
+	.byte	0	// DW_children_no
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x2	// (DW_AT_location)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.uleb128 0x2137	// (DW_AT_GNU_locviews)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x4	// (abbrev code)
+	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)
+	.byte	0	// DW_children_no
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x31	// (DW_AT_abstract_origin)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x5	// (abbrev code)
+	.uleb128 0x24	// (TAG: DW_TAG_base_type)
+	.byte	0	// DW_children_no
+	.uleb128 0xb	// (DW_AT_byte_size)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3e	// (DW_AT_encoding)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0x8	// (DW_FORM_string)
+	.byte	0
+	.byte	0
+	.uleb128 0x6	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0x8	// (DW_FORM_string)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x1	// (DW_AT_sibling)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x7	// (abbrev code)
+	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)
+	.byte	0	// DW_children_no
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x2115	// (DW_AT_GNU_tail_call)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x31	// (DW_AT_abstract_origin)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x8	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x1	// (DW_AT_sibling)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x9	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0	// DW_children_no
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.byte	0
+	.section	.debug_loc,"",@progbits
+.Ldebug_loc0:
+.LVUS0:
+	.uleb128 .LVU17	// View list begin (*.LVUS0)
+	.uleb128 .LVU18	// View list end (*.LVUS0)
+	.uleb128 .LVU18	// View list begin (*.LVUS0)
+	.uleb128 .LVU20	// View list end (*.LVUS0)
+	.uleb128 .LVU20	// View list begin (*.LVUS0)
+	.uleb128 0	// View list end (*.LVUS0)
+.LLST0:
+	.8byte	.LVL3	// Location list begin address (*.LLST0)
+	.8byte	.LVL3	// Location list end address (*.LLST0)
+	.2byte	0x1	// Location expression size
+	.byte	0x50	// DW_OP_reg0
+	.8byte	.LVL3	// Location list begin address (*.LLST0)
+	.8byte	.LVL4	// Location list end address (*.LLST0)
+	.2byte	0x3	// Location expression size
+	.byte	0x70	// DW_OP_breg0
+	.sleb128 1
+	.byte	0x9f	// DW_OP_stack_value
+	.8byte	.LVL4	// Location list begin address (*.LLST0)
+	.8byte	.LFE4	// Location list end address (*.LLST0)
+	.2byte	0x1	// Location expression size
+	.byte	0x50	// DW_OP_reg0
+	.8byte	0	// Location list terminator begin (*.LLST0)
+	.8byte	0	// Location list terminator end (*.LLST0)
+	.section	.debug_aranges,"",@progbits
+	.4byte	0x3c	// Length of Address Ranges Info
+	.2byte	0x2	// DWARF aranges version
+	.4byte	.Ldebug_info0	// Offset of Compilation Unit Info
+	.byte	0x8	// Size of Address
+	.byte	0	// Size of Segment Descriptor
+	.2byte	0	// Pad to 16 byte boundary
+	.2byte	0
+	.8byte	.Ltext0	// Address
+	.8byte	.Letext0-.Ltext0	// Length
+	.8byte	.LFB4	// Address
+	.8byte	.LFE4-.LFB4	// Length
+	.8byte	0
+	.8byte	0
+	.section	.debug_ranges,"",@progbits
+.Ldebug_ranges0:
+	.8byte	.Ltext0	// Offset 0
+	.8byte	.Letext0
+	.8byte	.LFB4	// Offset 0x10
+	.8byte	.LFE4
+	.8byte	0
+	.8byte	0
+	.section	.debug_line,"",@progbits
+.Ldebug_line0:
+	.section	.debug_str,"MS",@progbits,1
+.LASF6:
+	.string	"bar_1"
+.LASF2:
+	.string	"tailcall-only.c"
+.LASF3:
+	.string	"/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+.LASF5:
+	.string	"answer"
+.LASF4:
+	.string	"main"
+.LASF1:
+	.string	"GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"
+.LASF0:
+	.string	"foo_1"
+	.ident	"GCC: (Debian 10.2.1-3) 10.2.1 20201224"
+	.section	.note.GNU-stack,"",@progbits
diff --git a/gdb/testsuite/gdb.btrace/aarch64-tailcall.S b/gdb/testsuite/gdb.btrace/aarch64-tailcall.S
new file mode 100644
index 00000000000..2023b878a1a
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/aarch64-tailcall.S
@@ -0,0 +1,408 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.
+
+   This file has been generated on an armv8 machine using:
+   gcc -S -O2 -dA -g tailcall.c -o aarch64-tailcall.S  */
+
+	.arch armv8-a
+	.file	"tailcall.c"
+	.text
+.Ltext0:
+	.align	2
+	.p2align 4,,11
+	//.tune generic
+	.type	bar, %function
+bar:
+.LFB0:
+	.file 1 "tailcall.c"
+	// tailcall.c:22:1
+	.loc 1 22 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall.c:23:3
+	.loc 1 23 3 view .LVU1
+	// tailcall.c:24:1
+	.loc 1 24 1 is_stmt 0 view .LVU2
+	mov	w0, 42
+// SUCC: EXIT [always]  count:1073741824 (estimated locally)
+	ret
+	.cfi_endproc
+.LFE0:
+	.size	bar, .-bar
+	.align	2
+	.p2align 4,,11
+	.type	foo, %function
+foo:
+.LFB1:
+	// tailcall.c:28:1
+	.loc 1 28 1 is_stmt 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall.c:29:3
+	.loc 1 29 3 view .LVU4
+// SUCC: EXIT [always]  count:1073741824 (estimated locally) (ABNORMAL,SIBCALL)
+	// tailcall.c:29:10
+	.loc 1 29 10 is_stmt 0 view .LVU5
+	b	bar
+.LVL0:
+	.cfi_endproc
+.LFE1:
+	.size	foo, .-foo
+	.section	.text.startup,"ax",@progbits
+	.align	2
+	.p2align 4,,11
+	.global	main
+	.type	main, %function
+main:
+.LFB2:
+	// tailcall.c:34:1
+	.loc 1 34 1 is_stmt 1 view -0
+	.cfi_startproc
+// BLOCK 2, count:1073741824 (estimated locally) seq:0
+// PRED: ENTRY [always]  count:1073741824 (estimated locally) (FALLTHRU)
+	// tailcall.c:35:3
+	.loc 1 35 3 view .LVU7
+	// tailcall.c:37:3
+	.loc 1 37 3 view .LVU8
+	// tailcall.c:34:1
+	.loc 1 34 1 is_stmt 0 view .LVU9
+	stp	x29, x30, [sp, -16]!
+	.cfi_def_cfa_offset 16
+	.cfi_offset 29, -16
+	.cfi_offset 30, -8
+	mov	x29, sp
+	// tailcall.c:37:12
+	.loc 1 37 12 view .LVU10
+	bl	foo
+.LVL1:
+	// DEBUG answer => x0
+	// tailcall.c:38:3
+	.loc 1 38 3 is_stmt 1 view .LVU11
+	// DEBUG answer => x0+0x1
+	// tailcall.c:40:3
+	.loc 1 40 3 view .LVU12
+	// tailcall.c:41:1
+	.loc 1 41 1 is_stmt 0 view .LVU13
+	add	w0, w0, 1
+.LVL2:
+	// DEBUG answer => x0
+	// tailcall.c:41:1
+	.loc 1 41 1 view .LVU14
+	ldp	x29, x30, [sp], 16
+	.cfi_restore 30
+	.cfi_restore 29
+	.cfi_def_cfa_offset 0
+// SUCC: EXIT [always]  count:1073741824 (estimated locally)
+	ret
+	.cfi_endproc
+.LFE2:
+	.size	main, .-main
+	.text
+.Letext0:
+	.section	.debug_info,"",@progbits
+.Ldebug_info0:
+	.4byte	0xbf	// Length of Compilation Unit Info
+	.2byte	0x4	// DWARF version number
+	.4byte	.Ldebug_abbrev0	// Offset Into Abbrev. Section
+	.byte	0x8	// Pointer Size (in bytes)
+	.uleb128 0x1	// (DIE (0xb) DW_TAG_compile_unit)
+	.4byte	.LASF0	// DW_AT_producer: "GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"
+	.byte	0xc	// DW_AT_language
+	.4byte	.LASF1	// DW_AT_name: "tailcall.c"
+	.4byte	.LASF2	// DW_AT_comp_dir: "/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+	.4byte	.Ldebug_ranges0+0	// DW_AT_ranges
+	.8byte	0	// DW_AT_low_pc
+	.4byte	.Ldebug_line0	// DW_AT_stmt_list
+	.uleb128 0x2	// (DIE (0x29) DW_TAG_subprogram)
+			// DW_AT_external
+	.4byte	.LASF3	// DW_AT_name: "main"
+	.byte	0x1	// DW_AT_decl_file (tailcall.c)
+	.byte	0x21	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB2	// DW_AT_low_pc
+	.8byte	.LFE2-.LFB2	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.4byte	0x6d	// DW_AT_sibling
+	.uleb128 0x3	// (DIE (0x4b) DW_TAG_variable)
+	.4byte	.LASF4	// DW_AT_name: "answer"
+	.byte	0x1	// DW_AT_decl_file (tailcall.c)
+	.byte	0x23	// DW_AT_decl_line
+	.byte	0x7	// DW_AT_decl_column
+	.4byte	0x6d	// DW_AT_type
+	.4byte	.LLST0	// DW_AT_location
+	.4byte	.LVUS0	// DW_AT_GNU_locviews
+	.uleb128 0x4	// (DIE (0x5f) DW_TAG_GNU_call_site)
+	.8byte	.LVL1	// DW_AT_low_pc
+	.4byte	0x74	// DW_AT_abstract_origin
+	.byte	0	// end of children of DIE 0x29
+	.uleb128 0x5	// (DIE (0x6d) DW_TAG_base_type)
+	.byte	0x4	// DW_AT_byte_size
+	.byte	0x5	// DW_AT_encoding
+	.ascii "int\0"	// DW_AT_name
+	.uleb128 0x6	// (DIE (0x74) DW_TAG_subprogram)
+	.ascii "foo\0"	// DW_AT_name
+	.byte	0x1	// DW_AT_decl_file (tailcall.c)
+	.byte	0x1b	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB1	// DW_AT_low_pc
+	.8byte	.LFE1-.LFB1	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.4byte	0xa4	// DW_AT_sibling
+	.uleb128 0x7	// (DIE (0x96) DW_TAG_GNU_call_site)
+	.8byte	.LVL0	// DW_AT_low_pc
+			// DW_AT_GNU_tail_call
+	.4byte	0xa4	// DW_AT_abstract_origin
+	.byte	0	// end of children of DIE 0x74
+	.uleb128 0x8	// (DIE (0xa4) DW_TAG_subprogram)
+	.ascii "bar\0"	// DW_AT_name
+	.byte	0x1	// DW_AT_decl_file (tailcall.c)
+	.byte	0x15	// DW_AT_decl_line
+	.byte	0x1	// DW_AT_decl_column
+			// DW_AT_prototyped
+	.4byte	0x6d	// DW_AT_type
+	.8byte	.LFB0	// DW_AT_low_pc
+	.8byte	.LFE0-.LFB0	// DW_AT_high_pc
+	.uleb128 0x1	// DW_AT_frame_base
+	.byte	0x9c	// DW_OP_call_frame_cfa
+			// DW_AT_GNU_all_call_sites
+	.byte	0	// end of children of DIE 0xb
+	.section	.debug_abbrev,"",@progbits
+.Ldebug_abbrev0:
+	.uleb128 0x1	// (abbrev code)
+	.uleb128 0x11	// (TAG: DW_TAG_compile_unit)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x25	// (DW_AT_producer)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x13	// (DW_AT_language)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x1b	// (DW_AT_comp_dir)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x55	// (DW_AT_ranges)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x10	// (DW_AT_stmt_list)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x2	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x3f	// (DW_AT_external)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x1	// (DW_AT_sibling)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x3	// (abbrev code)
+	.uleb128 0x34	// (TAG: DW_TAG_variable)
+	.byte	0	// DW_children_no
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0xe	// (DW_FORM_strp)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x2	// (DW_AT_location)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.uleb128 0x2137	// (DW_AT_GNU_locviews)
+	.uleb128 0x17	// (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x4	// (abbrev code)
+	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)
+	.byte	0	// DW_children_no
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x31	// (DW_AT_abstract_origin)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x5	// (abbrev code)
+	.uleb128 0x24	// (TAG: DW_TAG_base_type)
+	.byte	0	// DW_children_no
+	.uleb128 0xb	// (DW_AT_byte_size)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3e	// (DW_AT_encoding)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0x8	// (DW_FORM_string)
+	.byte	0
+	.byte	0
+	.uleb128 0x6	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0x1	// DW_children_yes
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0x8	// (DW_FORM_string)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x1	// (DW_AT_sibling)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x7	// (abbrev code)
+	.uleb128 0x4109	// (TAG: DW_TAG_GNU_call_site)
+	.byte	0	// DW_children_no
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x2115	// (DW_AT_GNU_tail_call)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x31	// (DW_AT_abstract_origin)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x8	// (abbrev code)
+	.uleb128 0x2e	// (TAG: DW_TAG_subprogram)
+	.byte	0	// DW_children_no
+	.uleb128 0x3	// (DW_AT_name)
+	.uleb128 0x8	// (DW_FORM_string)
+	.uleb128 0x3a	// (DW_AT_decl_file)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x3b	// (DW_AT_decl_line)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x39	// (DW_AT_decl_column)
+	.uleb128 0xb	// (DW_FORM_data1)
+	.uleb128 0x27	// (DW_AT_prototyped)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.uleb128 0x49	// (DW_AT_type)
+	.uleb128 0x13	// (DW_FORM_ref4)
+	.uleb128 0x11	// (DW_AT_low_pc)
+	.uleb128 0x1	// (DW_FORM_addr)
+	.uleb128 0x12	// (DW_AT_high_pc)
+	.uleb128 0x7	// (DW_FORM_data8)
+	.uleb128 0x40	// (DW_AT_frame_base)
+	.uleb128 0x18	// (DW_FORM_exprloc)
+	.uleb128 0x2117	// (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	// (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.byte	0
+	.section	.debug_loc,"",@progbits
+.Ldebug_loc0:
+.LVUS0:
+	.uleb128 .LVU11	// View list begin (*.LVUS0)
+	.uleb128 .LVU12	// View list end (*.LVUS0)
+	.uleb128 .LVU12	// View list begin (*.LVUS0)
+	.uleb128 .LVU14	// View list end (*.LVUS0)
+	.uleb128 .LVU14	// View list begin (*.LVUS0)
+	.uleb128 0	// View list end (*.LVUS0)
+.LLST0:
+	.8byte	.LVL1	// Location list begin address (*.LLST0)
+	.8byte	.LVL1	// Location list end address (*.LLST0)
+	.2byte	0x1	// Location expression size
+	.byte	0x50	// DW_OP_reg0
+	.8byte	.LVL1	// Location list begin address (*.LLST0)
+	.8byte	.LVL2	// Location list end address (*.LLST0)
+	.2byte	0x3	// Location expression size
+	.byte	0x70	// DW_OP_breg0
+	.sleb128 1
+	.byte	0x9f	// DW_OP_stack_value
+	.8byte	.LVL2	// Location list begin address (*.LLST0)
+	.8byte	.LFE2	// Location list end address (*.LLST0)
+	.2byte	0x1	// Location expression size
+	.byte	0x50	// DW_OP_reg0
+	.8byte	0	// Location list terminator begin (*.LLST0)
+	.8byte	0	// Location list terminator end (*.LLST0)
+	.section	.debug_aranges,"",@progbits
+	.4byte	0x3c	// Length of Address Ranges Info
+	.2byte	0x2	// DWARF aranges version
+	.4byte	.Ldebug_info0	// Offset of Compilation Unit Info
+	.byte	0x8	// Size of Address
+	.byte	0	// Size of Segment Descriptor
+	.2byte	0	// Pad to 16 byte boundary
+	.2byte	0
+	.8byte	.Ltext0	// Address
+	.8byte	.Letext0-.Ltext0	// Length
+	.8byte	.LFB2	// Address
+	.8byte	.LFE2-.LFB2	// Length
+	.8byte	0
+	.8byte	0
+	.section	.debug_ranges,"",@progbits
+.Ldebug_ranges0:
+	.8byte	.Ltext0	// Offset 0
+	.8byte	.Letext0
+	.8byte	.LFB2	// Offset 0x10
+	.8byte	.LFE2
+	.8byte	0
+	.8byte	0
+	.section	.debug_line,"",@progbits
+.Ldebug_line0:
+	.section	.debug_str,"MS",@progbits,1
+.LASF0:
+	.string	"GNU C17 10.2.1 20201224 -mlittle-endian -mabi=lp64 -g -O2 -fasynchronous-unwind-tables"
+.LASF2:
+	.string	"/home/linaro/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+.LASF4:
+	.string	"answer"
+.LASF1:
+	.string	"tailcall.c"
+.LASF3:
+	.string	"main"
+	.ident	"GCC: (Debian 10.2.1-3) 10.2.1 20201224"
+	.section	.note.GNU-stack,"",@progbits
diff --git a/gdb/testsuite/gdb.btrace/arm-instruction_history.S b/gdb/testsuite/gdb.btrace/arm-instruction_history.S
new file mode 100644
index 00000000000..16ef0356993
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/arm-instruction_history.S
@@ -0,0 +1,31 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.  */
+
+.arm
+.text
+.globl loop
+.type  loop, %function
+loop:
+	movs r0, #2 /* bp.1 */
+L1:
+	cmp r0, #0
+	beq L2
+	subs r0, r0, #1
+	b L1
+L2:
+	bx lr /* bp.2 */
+
diff --git a/gdb/testsuite/gdb.btrace/arm-record_goto.S b/gdb/testsuite/gdb.btrace/arm-record_goto.S
new file mode 100644
index 00000000000..d68f1187a74
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/arm-record_goto.S
@@ -0,0 +1,432 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.
+
+   This file has been generated on an armv7 machine using:
+   gcc -S -dA -g record_goto.c -o arm-record_goto.S  */
+
+	.arch armv7-a
+	.eabi_attribute 28, 1	@ Tag_ABI_VFP_args
+	.eabi_attribute 20, 1	@ Tag_ABI_FP_denormal
+	.eabi_attribute 21, 1	@ Tag_ABI_FP_exceptions
+	.eabi_attribute 23, 3	@ Tag_ABI_FP_number_model
+	.eabi_attribute 24, 1	@ Tag_ABI_align8_needed
+	.eabi_attribute 25, 1	@ Tag_ABI_align8_preserved
+	.eabi_attribute 26, 2	@ Tag_ABI_enum_size
+	.eabi_attribute 30, 6	@ Tag_ABI_optimization_goals
+	.eabi_attribute 34, 1	@ Tag_CPU_unaligned_access
+	.eabi_attribute 18, 4	@ Tag_ABI_PCS_wchar_t
+	.file	"record_goto.c"
+	.text
+.Ltext0:
+	.cfi_sections	.debug_frame
+	.align	1
+	.global	fun1
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	fun1, %function
+fun1:
+.LFB0:
+	.file 1 "record_goto.c"
+	@ record_goto.c:22
+	.loc 1 22 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 1, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 seq:0
+@ PRED: ENTRY (FALLTHRU)
+	push	{r7}
+	.cfi_def_cfa_offset 4
+	.cfi_offset 7, -4
+	add	r7, sp, #0
+	.cfi_def_cfa_register 7
+	@ record_goto.c:23
+	.loc 1 23 0
+	nop
+	mov	sp, r7
+	.cfi_def_cfa_register 13
+	@ sp needed
+	ldr	r7, [sp], #4
+	.cfi_restore 7
+	.cfi_def_cfa_offset 0
+@ SUCC: EXIT [100.0%] 
+	bx	lr
+	.cfi_endproc
+.LFE0:
+	.size	fun1, .-fun1
+	.align	1
+	.global	fun2
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	fun2, %function
+fun2:
+.LFB1:
+	@ record_goto.c:27
+	.loc 1 27 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 1, uses_anonymous_args = 0
+@ BLOCK 2 seq:0
+@ PRED: ENTRY (FALLTHRU)
+	push	{r7, lr}
+	.cfi_def_cfa_offset 8
+	.cfi_offset 7, -8
+	.cfi_offset 14, -4
+	add	r7, sp, #0
+	.cfi_def_cfa_register 7
+	@ record_goto.c:28
+	.loc 1 28 0
+	bl	fun1(PLT)
+	@ record_goto.c:29
+	.loc 1 29 0
+	nop
+@ SUCC: EXIT [100.0%] 
+	pop	{r7, pc}
+	.cfi_endproc
+.LFE1:
+	.size	fun2, .-fun2
+	.align	1
+	.global	fun3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	fun3, %function
+fun3:
+.LFB2:
+	@ record_goto.c:33
+	.loc 1 33 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 1, uses_anonymous_args = 0
+@ BLOCK 2 seq:0
+@ PRED: ENTRY (FALLTHRU)
+	push	{r7, lr}
+	.cfi_def_cfa_offset 8
+	.cfi_offset 7, -8
+	.cfi_offset 14, -4
+	add	r7, sp, #0
+	.cfi_def_cfa_register 7
+	@ record_goto.c:34
+	.loc 1 34 0
+	bl	fun1(PLT)
+	@ record_goto.c:35
+	.loc 1 35 0
+	bl	fun2(PLT)
+	@ record_goto.c:36
+	.loc 1 36 0
+	nop
+@ SUCC: EXIT [100.0%] 
+	pop	{r7, pc}
+	.cfi_endproc
+.LFE2:
+	.size	fun3, .-fun3
+	.align	1
+	.global	fun4
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	fun4, %function
+fun4:
+.LFB3:
+	@ record_goto.c:40
+	.loc 1 40 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 1, uses_anonymous_args = 0
+@ BLOCK 2 seq:0
+@ PRED: ENTRY (FALLTHRU)
+	push	{r7, lr}
+	.cfi_def_cfa_offset 8
+	.cfi_offset 7, -8
+	.cfi_offset 14, -4
+	add	r7, sp, #0
+	.cfi_def_cfa_register 7
+	@ record_goto.c:41
+	.loc 1 41 0
+	bl	fun1(PLT)
+	@ record_goto.c:42
+	.loc 1 42 0
+	bl	fun2(PLT)
+	@ record_goto.c:43
+	.loc 1 43 0
+	bl	fun3(PLT)
+	@ record_goto.c:44
+	.loc 1 44 0
+	nop
+@ SUCC: EXIT [100.0%] 
+	pop	{r7, pc}
+	.cfi_endproc
+.LFE3:
+	.size	fun4, .-fun4
+	.align	1
+	.global	main
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	main, %function
+main:
+.LFB4:
+	@ record_goto.c:48
+	.loc 1 48 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 1, uses_anonymous_args = 0
+@ BLOCK 2 seq:0
+@ PRED: ENTRY (FALLTHRU)
+	push	{r7, lr}
+	.cfi_def_cfa_offset 8
+	.cfi_offset 7, -8
+	.cfi_offset 14, -4
+	add	r7, sp, #0
+	.cfi_def_cfa_register 7
+	@ record_goto.c:49
+	.loc 1 49 0
+	bl	fun4(PLT)
+	@ record_goto.c:50
+	.loc 1 50 0
+	movs	r3, #0
+	@ record_goto.c:51
+	.loc 1 51 0
+	mov	r0, r3
+@ SUCC: EXIT [100.0%] 
+	pop	{r7, pc}
+	.cfi_endproc
+.LFE4:
+	.size	main, .-main
+.Letext0:
+	.section	.debug_info,"",%progbits
+.Ldebug_info0:
+	.4byte	0x82	@ Length of Compilation Unit Info
+	.2byte	0x4	@ DWARF version number
+	.4byte	.Ldebug_abbrev0	@ Offset Into Abbrev. Section
+	.byte	0x4	@ Pointer Size (in bytes)
+	.uleb128 0x1	@ (DIE (0xb) DW_TAG_compile_unit)
+	.4byte	.LASF4	@ DW_AT_producer: "GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -fstack-protector-strong"
+	.byte	0xc	@ DW_AT_language
+	.4byte	.LASF5	@ DW_AT_name: "record_goto.c"
+	.4byte	.LASF6	@ DW_AT_comp_dir: "/home/ubuntu/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+	.4byte	.Ltext0	@ DW_AT_low_pc
+	.4byte	.Letext0-.Ltext0	@ DW_AT_high_pc
+	.4byte	.Ldebug_line0	@ DW_AT_stmt_list
+	.uleb128 0x2	@ (DIE (0x25) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF7	@ DW_AT_name: "main"
+	.byte	0x1	@ DW_AT_decl_file (record_goto.c)
+	.byte	0x2f	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x3a	@ DW_AT_type
+	.4byte	.LFB4	@ DW_AT_low_pc
+	.4byte	.LFE4-.LFB4	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x3	@ (DIE (0x3a) DW_TAG_base_type)
+	.byte	0x4	@ DW_AT_byte_size
+	.byte	0x5	@ DW_AT_encoding
+	.ascii "int\0"	@ DW_AT_name
+	.uleb128 0x4	@ (DIE (0x41) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF0	@ DW_AT_name: "fun4"
+	.byte	0x1	@ DW_AT_decl_file (record_goto.c)
+	.byte	0x27	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	.LFB3	@ DW_AT_low_pc
+	.4byte	.LFE3-.LFB3	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x4	@ (DIE (0x52) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF1	@ DW_AT_name: "fun3"
+	.byte	0x1	@ DW_AT_decl_file (record_goto.c)
+	.byte	0x20	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	.LFB2	@ DW_AT_low_pc
+	.4byte	.LFE2-.LFB2	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x4	@ (DIE (0x63) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF2	@ DW_AT_name: "fun2"
+	.byte	0x1	@ DW_AT_decl_file (record_goto.c)
+	.byte	0x1a	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	.LFB1	@ DW_AT_low_pc
+	.4byte	.LFE1-.LFB1	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_tail_call_sites
+	.uleb128 0x5	@ (DIE (0x74) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF3	@ DW_AT_name: "fun1"
+	.byte	0x1	@ DW_AT_decl_file (record_goto.c)
+	.byte	0x15	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	.LFB0	@ DW_AT_low_pc
+	.4byte	.LFE0-.LFB0	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.byte	0	@ end of children of DIE 0xb
+	.section	.debug_abbrev,"",%progbits
+.Ldebug_abbrev0:
+	.uleb128 0x1	@ (abbrev code)
+	.uleb128 0x11	@ (TAG: DW_TAG_compile_unit)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x25	@ (DW_AT_producer)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x13	@ (DW_AT_language)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x1b	@ (DW_AT_comp_dir)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x10	@ (DW_AT_stmt_list)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x2	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3f	@ (DW_AT_external)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2116	@ (DW_AT_GNU_all_tail_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.uleb128 0x3	@ (abbrev code)
+	.uleb128 0x24	@ (TAG: DW_TAG_base_type)
+	.byte	0	@ DW_children_no
+	.uleb128 0xb	@ (DW_AT_byte_size)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3e	@ (DW_AT_encoding)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0x8	@ (DW_FORM_string)
+	.byte	0
+	.byte	0
+	.uleb128 0x4	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3f	@ (DW_AT_external)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2116	@ (DW_AT_GNU_all_tail_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.uleb128 0x5	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3f	@ (DW_AT_external)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.byte	0
+	.section	.debug_aranges,"",%progbits
+	.4byte	0x1c	@ Length of Address Ranges Info
+	.2byte	0x2	@ DWARF Version
+	.4byte	.Ldebug_info0	@ Offset of Compilation Unit Info
+	.byte	0x4	@ Size of Address
+	.byte	0	@ Size of Segment Descriptor
+	.2byte	0	@ Pad to 8 byte boundary
+	.2byte	0
+	.4byte	.Ltext0	@ Address
+	.4byte	.Letext0-.Ltext0	@ Length
+	.4byte	0
+	.4byte	0
+	.section	.debug_line,"",%progbits
+.Ldebug_line0:
+	.section	.debug_str,"MS",%progbits,1
+.LASF5:
+	.ascii	"record_goto.c\000"
+.LASF2:
+	.ascii	"fun2\000"
+.LASF6:
+	.ascii	"/home/ubuntu/development/gdb/binutils-gdb/gdb/tests"
+	.ascii	"uite/gdb.btrace\000"
+.LASF4:
+	.ascii	"GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu"
+	.ascii	"=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -fstack-pro"
+	.ascii	"tector-strong\000"
+.LASF0:
+	.ascii	"fun4\000"
+.LASF3:
+	.ascii	"fun1\000"
+.LASF7:
+	.ascii	"main\000"
+.LASF1:
+	.ascii	"fun3\000"
+	.ident	"GCC: (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0"
+	.section	.note.GNU-stack,"",%progbits
diff --git a/gdb/testsuite/gdb.btrace/arm-tailcall-only.S b/gdb/testsuite/gdb.btrace/arm-tailcall-only.S
new file mode 100644
index 00000000000..73a89c6e533
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/arm-tailcall-only.S
@@ -0,0 +1,503 @@ 
+/* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2016-2020 Free Software Foundation, Inc.
+
+   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/>.
+
+   This file has been generated on an armv7 machine using:
+   gcc -S -O2 -dA -g tailcall-only.c -o arm-tailcall-only.S  */
+
+	.eabi_attribute 28, 1	@ Tag_ABI_VFP_args
+	.eabi_attribute 20, 1	@ Tag_ABI_FP_denormal
+	.eabi_attribute 21, 1	@ Tag_ABI_FP_exceptions
+	.eabi_attribute 23, 3	@ Tag_ABI_FP_number_model
+	.eabi_attribute 24, 1	@ Tag_ABI_align8_needed
+	.eabi_attribute 25, 1	@ Tag_ABI_align8_preserved
+	.eabi_attribute 26, 2	@ Tag_ABI_enum_size
+	.eabi_attribute 30, 2	@ Tag_ABI_optimization_goals
+	.eabi_attribute 34, 1	@ Tag_CPU_unaligned_access
+	.eabi_attribute 18, 4	@ Tag_ABI_PCS_wchar_t
+	.file	"tailcall-only.c"
+	.text
+.Ltext0:
+	.cfi_sections	.debug_frame
+	.align	1
+	.p2align 2,,3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	bar_1, %function
+bar_1:
+.LFB0:
+	.file 1 "tailcall-only.c"
+	@ tailcall-only.c:22
+	.loc 1 22 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+	@ tailcall-only.c:24
+	.loc 1 24 0
+	movs	r0, #42
+@ SUCC: EXIT [100.0%] 
+	bx	lr
+	.cfi_endproc
+.LFE0:
+	.size	bar_1, .-bar_1
+	.align	1
+	.p2align 2,,3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	bar, %function
+bar:
+.LFB1:
+	@ tailcall-only.c:28
+	.loc 1 28 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)
+	@ tailcall-only.c:29
+	.loc 1 29 0
+	b	bar_1(PLT)
+.LVL0:
+	.cfi_endproc
+.LFE1:
+	.size	bar, .-bar
+	.align	1
+	.p2align 2,,3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	foo_1, %function
+foo_1:
+.LFB2:
+	@ tailcall-only.c:34
+	.loc 1 34 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)
+	@ tailcall-only.c:35
+	.loc 1 35 0
+	b	bar(PLT)
+.LVL1:
+	.cfi_endproc
+.LFE2:
+	.size	foo_1, .-foo_1
+	.align	1
+	.p2align 2,,3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	foo, %function
+foo:
+.LFB3:
+	@ tailcall-only.c:40
+	.loc 1 40 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)
+	@ tailcall-only.c:41
+	.loc 1 41 0
+	b	foo_1(PLT)
+.LVL2:
+	.cfi_endproc
+.LFE3:
+	.size	foo, .-foo
+	.section	.text.startup,"ax",%progbits
+	.align	1
+	.p2align 2,,3
+	.global	main
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	main, %function
+main:
+.LFB4:
+	@ tailcall-only.c:46
+	.loc 1 46 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+	push	{r3, lr}
+	.cfi_def_cfa_offset 8
+	.cfi_offset 3, -8
+	.cfi_offset 14, -4
+	@ tailcall-only.c:49
+	.loc 1 49 0
+	bl	foo(PLT)
+.LVL3:
+	@ tailcall-only.c:53
+	.loc 1 53 0
+	adds	r0, r0, #1
+.LVL4:
+@ SUCC: EXIT [100.0%] 
+	pop	{r3, pc}
+	.cfi_endproc
+.LFE4:
+	.size	main, .-main
+	.text
+.Letext0:
+	.section	.debug_info,"",%progbits
+.Ldebug_info0:
+	.4byte	0xd9	@ Length of Compilation Unit Info
+	.2byte	0x4	@ DWARF version number
+	.4byte	.Ldebug_abbrev0	@ Offset Into Abbrev. Section
+	.byte	0x4	@ Pointer Size (in bytes)
+	.uleb128 0x1	@ (DIE (0xb) DW_TAG_compile_unit)
+	.4byte	.LASF1	@ DW_AT_producer: "GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack-protector-strong"
+	.byte	0xc	@ DW_AT_language
+	.4byte	.LASF2	@ DW_AT_name: "tailcall-only.c"
+	.4byte	.LASF3	@ DW_AT_comp_dir: "/home/ubuntu/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+	.4byte	.Ldebug_ranges0+0	@ DW_AT_ranges
+	.4byte	0	@ DW_AT_low_pc
+	.4byte	.Ldebug_line0	@ DW_AT_stmt_list
+	.uleb128 0x2	@ (DIE (0x25) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF4	@ DW_AT_name: "main"
+	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)
+	.byte	0x2d	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB4	@ DW_AT_low_pc
+	.4byte	.LFE4-.LFB4	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.4byte	0x57	@ DW_AT_sibling
+	.uleb128 0x3	@ (DIE (0x3e) DW_TAG_variable)
+	.4byte	.LASF5	@ DW_AT_name: "answer"
+	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)
+	.byte	0x2f	@ DW_AT_decl_line
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LLST0	@ DW_AT_location
+	.uleb128 0x4	@ (DIE (0x4d) DW_TAG_GNU_call_site)
+	.4byte	.LVL3	@ DW_AT_low_pc
+	.4byte	0x5e	@ DW_AT_abstract_origin
+	.byte	0	@ end of children of DIE 0x25
+	.uleb128 0x5	@ (DIE (0x57) DW_TAG_base_type)
+	.byte	0x4	@ DW_AT_byte_size
+	.byte	0x5	@ DW_AT_encoding
+	.ascii "int\0"	@ DW_AT_name
+	.uleb128 0x6	@ (DIE (0x5e) DW_TAG_subprogram)
+	.ascii "foo\0"	@ DW_AT_name
+	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)
+	.byte	0x27	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB3	@ DW_AT_low_pc
+	.4byte	.LFE3-.LFB3	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.4byte	0x81	@ DW_AT_sibling
+	.uleb128 0x7	@ (DIE (0x77) DW_TAG_GNU_call_site)
+	.4byte	.LVL2	@ DW_AT_low_pc
+			@ DW_AT_GNU_tail_call
+	.4byte	0x81	@ DW_AT_abstract_origin
+	.byte	0	@ end of children of DIE 0x5e
+	.uleb128 0x8	@ (DIE (0x81) DW_TAG_subprogram)
+	.4byte	.LASF0	@ DW_AT_name: "foo_1"
+	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)
+	.byte	0x21	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB2	@ DW_AT_low_pc
+	.4byte	.LFE2-.LFB2	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.4byte	0xa4	@ DW_AT_sibling
+	.uleb128 0x7	@ (DIE (0x9a) DW_TAG_GNU_call_site)
+	.4byte	.LVL1	@ DW_AT_low_pc
+			@ DW_AT_GNU_tail_call
+	.4byte	0xa4	@ DW_AT_abstract_origin
+	.byte	0	@ end of children of DIE 0x81
+	.uleb128 0x6	@ (DIE (0xa4) DW_TAG_subprogram)
+	.ascii "bar\0"	@ DW_AT_name
+	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)
+	.byte	0x1b	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB1	@ DW_AT_low_pc
+	.4byte	.LFE1-.LFB1	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.4byte	0xc7	@ DW_AT_sibling
+	.uleb128 0x7	@ (DIE (0xbd) DW_TAG_GNU_call_site)
+	.4byte	.LVL0	@ DW_AT_low_pc
+			@ DW_AT_GNU_tail_call
+	.4byte	0xc7	@ DW_AT_abstract_origin
+	.byte	0	@ end of children of DIE 0xa4
+	.uleb128 0x9	@ (DIE (0xc7) DW_TAG_subprogram)
+	.4byte	.LASF6	@ DW_AT_name: "bar_1"
+	.byte	0x1	@ DW_AT_decl_file (tailcall-only.c)
+	.byte	0x15	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB0	@ DW_AT_low_pc
+	.4byte	.LFE0-.LFB0	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.byte	0	@ end of children of DIE 0xb
+	.section	.debug_abbrev,"",%progbits
+.Ldebug_abbrev0:
+	.uleb128 0x1	@ (abbrev code)
+	.uleb128 0x11	@ (TAG: DW_TAG_compile_unit)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x25	@ (DW_AT_producer)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x13	@ (DW_AT_language)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x1b	@ (DW_AT_comp_dir)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x55	@ (DW_AT_ranges)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x10	@ (DW_AT_stmt_list)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x2	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x3f	@ (DW_AT_external)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x1	@ (DW_AT_sibling)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x3	@ (abbrev code)
+	.uleb128 0x34	@ (TAG: DW_TAG_variable)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x2	@ (DW_AT_location)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x4	@ (abbrev code)
+	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)
+	.byte	0	@ DW_children_no
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x31	@ (DW_AT_abstract_origin)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x5	@ (abbrev code)
+	.uleb128 0x24	@ (TAG: DW_TAG_base_type)
+	.byte	0	@ DW_children_no
+	.uleb128 0xb	@ (DW_AT_byte_size)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3e	@ (DW_AT_encoding)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0x8	@ (DW_FORM_string)
+	.byte	0
+	.byte	0
+	.uleb128 0x6	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0x8	@ (DW_FORM_string)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x1	@ (DW_AT_sibling)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x7	@ (abbrev code)
+	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)
+	.byte	0	@ DW_children_no
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x2115	@ (DW_AT_GNU_tail_call)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x31	@ (DW_AT_abstract_origin)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x8	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x1	@ (DW_AT_sibling)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x9	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.byte	0
+	.section	.debug_loc,"",%progbits
+.Ldebug_loc0:
+.LLST0:
+	.4byte	.LVL3	@ Location list begin address (*.LLST0)
+	.4byte	.LVL4	@ Location list end address (*.LLST0)
+	.2byte	0x3	@ Location expression size
+	.byte	0x70	@ DW_OP_breg0
+	.sleb128 1
+	.byte	0x9f	@ DW_OP_stack_value
+	.4byte	.LVL4	@ Location list begin address (*.LLST0)
+	.4byte	.LFE4	@ Location list end address (*.LLST0)
+	.2byte	0x1	@ Location expression size
+	.byte	0x50	@ DW_OP_reg0
+	.4byte	0	@ Location list terminator begin (*.LLST0)
+	.4byte	0	@ Location list terminator end (*.LLST0)
+	.section	.debug_aranges,"",%progbits
+	.4byte	0x24	@ Length of Address Ranges Info
+	.2byte	0x2	@ DWARF Version
+	.4byte	.Ldebug_info0	@ Offset of Compilation Unit Info
+	.byte	0x4	@ Size of Address
+	.byte	0	@ Size of Segment Descriptor
+	.2byte	0	@ Pad to 8 byte boundary
+	.2byte	0
+	.4byte	.Ltext0	@ Address
+	.4byte	.Letext0-.Ltext0	@ Length
+	.4byte	.LFB4	@ Address
+	.4byte	.LFE4-.LFB4	@ Length
+	.4byte	0
+	.4byte	0
+	.section	.debug_ranges,"",%progbits
+.Ldebug_ranges0:
+	.4byte	.Ltext0	@ Offset 0
+	.4byte	.Letext0
+	.4byte	.LFB4	@ Offset 0x8
+	.4byte	.LFE4
+	.4byte	0
+	.4byte	0
+	.section	.debug_line,"",%progbits
+.Ldebug_line0:
+	.section	.debug_str,"MS",%progbits,1
+.LASF2:
+	.ascii	"tailcall-only.c\000"
+.LASF5:
+	.ascii	"answer\000"
+.LASF1:
+	.ascii	"GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu"
+	.ascii	"=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack"
+	.ascii	"-protector-strong\000"
+.LASF4:
+	.ascii	"main\000"
+.LASF6:
+	.ascii	"bar_1\000"
+.LASF3:
+	.ascii	"/home/ubuntu/development/gdb/binutils-gdb/gdb/tests"
+	.ascii	"uite/gdb.btrace\000"
+.LASF0:
+	.ascii	"foo_1\000"
+	.ident	"GCC: (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0"
+	.section	.note.GNU-stack,"",%progbits
diff --git a/gdb/testsuite/gdb.btrace/arm-tailcall.S b/gdb/testsuite/gdb.btrace/arm-tailcall.S
new file mode 100644
index 00000000000..2f72dd12296
--- /dev/null
+++ b/gdb/testsuite/gdb.btrace/arm-tailcall.S
@@ -0,0 +1,390 @@ 
+ /* This testcase is part of GDB, the GNU debugger.
+
+   Copyright 2021 Free Software Foundation, Inc.
+
+   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/>.
+
+   This file has been generated on an armv7 machine using:
+   gcc -S -O2 -dA -g tailcall.c -o arm-tailcall.S  */
+
+	.eabi_attribute 28, 1	@ Tag_ABI_VFP_args
+	.eabi_attribute 20, 1	@ Tag_ABI_FP_denormal
+	.eabi_attribute 21, 1	@ Tag_ABI_FP_exceptions
+	.eabi_attribute 23, 3	@ Tag_ABI_FP_number_model
+	.eabi_attribute 24, 1	@ Tag_ABI_align8_needed
+	.eabi_attribute 25, 1	@ Tag_ABI_align8_preserved
+	.eabi_attribute 26, 2	@ Tag_ABI_enum_size
+	.eabi_attribute 30, 2	@ Tag_ABI_optimization_goals
+	.eabi_attribute 34, 1	@ Tag_CPU_unaligned_access
+	.eabi_attribute 18, 4	@ Tag_ABI_PCS_wchar_t
+	.file	"tailcall.c"
+	.text
+.Ltext0:
+	.cfi_sections	.debug_frame
+	.align	1
+	.p2align 2,,3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	bar, %function
+bar:
+.LFB0:
+	.file 1 "tailcall.c"
+	@ tailcall.c:22
+	.loc 1 22 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+	@ tailcall.c:24
+	.loc 1 24 0
+	movs	r0, #42
+@ SUCC: EXIT [100.0%] 
+	bx	lr
+	.cfi_endproc
+.LFE0:
+	.size	bar, .-bar
+	.align	1
+	.p2align 2,,3
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	foo, %function
+foo:
+.LFB1:
+	@ tailcall.c:28
+	.loc 1 28 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+	@ link register save eliminated.
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+@ SUCC: EXIT [100.0%]  (ABNORMAL,SIBCALL)
+	@ tailcall.c:29
+	.loc 1 29 0
+	b	bar(PLT)
+.LVL0:
+	.cfi_endproc
+.LFE1:
+	.size	foo, .-foo
+	.section	.text.startup,"ax",%progbits
+	.align	1
+	.p2align 2,,3
+	.global	main
+	.syntax unified
+	.thumb
+	.thumb_func
+	.fpu vfpv3-d16
+	.type	main, %function
+main:
+.LFB2:
+	@ tailcall.c:34
+	.loc 1 34 0
+	.cfi_startproc
+	@ args = 0, pretend = 0, frame = 0
+	@ frame_needed = 0, uses_anonymous_args = 0
+@ BLOCK 2 freq:10000 seq:0
+@ PRED: ENTRY [100.0%]  (FALLTHRU)
+	push	{r3, lr}
+	.cfi_def_cfa_offset 8
+	.cfi_offset 3, -8
+	.cfi_offset 14, -4
+	@ tailcall.c:37
+	.loc 1 37 0
+	bl	foo(PLT)
+.LVL1:
+	@ tailcall.c:41
+	.loc 1 41 0
+	adds	r0, r0, #1
+.LVL2:
+@ SUCC: EXIT [100.0%] 
+	pop	{r3, pc}
+	.cfi_endproc
+.LFE2:
+	.size	main, .-main
+	.text
+.Letext0:
+	.section	.debug_info,"",%progbits
+.Ldebug_info0:
+	.4byte	0x93	@ Length of Compilation Unit Info
+	.2byte	0x4	@ DWARF version number
+	.4byte	.Ldebug_abbrev0	@ Offset Into Abbrev. Section
+	.byte	0x4	@ Pointer Size (in bytes)
+	.uleb128 0x1	@ (DIE (0xb) DW_TAG_compile_unit)
+	.4byte	.LASF0	@ DW_AT_producer: "GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack-protector-strong"
+	.byte	0xc	@ DW_AT_language
+	.4byte	.LASF1	@ DW_AT_name: "tailcall.c"
+	.4byte	.LASF2	@ DW_AT_comp_dir: "/home/ubuntu/development/gdb/binutils-gdb/gdb/testsuite/gdb.btrace"
+	.4byte	.Ldebug_ranges0+0	@ DW_AT_ranges
+	.4byte	0	@ DW_AT_low_pc
+	.4byte	.Ldebug_line0	@ DW_AT_stmt_list
+	.uleb128 0x2	@ (DIE (0x25) DW_TAG_subprogram)
+			@ DW_AT_external
+	.4byte	.LASF3	@ DW_AT_name: "main"
+	.byte	0x1	@ DW_AT_decl_file (tailcall.c)
+	.byte	0x21	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB2	@ DW_AT_low_pc
+	.4byte	.LFE2-.LFB2	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.4byte	0x57	@ DW_AT_sibling
+	.uleb128 0x3	@ (DIE (0x3e) DW_TAG_variable)
+	.4byte	.LASF4	@ DW_AT_name: "answer"
+	.byte	0x1	@ DW_AT_decl_file (tailcall.c)
+	.byte	0x23	@ DW_AT_decl_line
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LLST0	@ DW_AT_location
+	.uleb128 0x4	@ (DIE (0x4d) DW_TAG_GNU_call_site)
+	.4byte	.LVL1	@ DW_AT_low_pc
+	.4byte	0x5e	@ DW_AT_abstract_origin
+	.byte	0	@ end of children of DIE 0x25
+	.uleb128 0x5	@ (DIE (0x57) DW_TAG_base_type)
+	.byte	0x4	@ DW_AT_byte_size
+	.byte	0x5	@ DW_AT_encoding
+	.ascii "int\0"	@ DW_AT_name
+	.uleb128 0x6	@ (DIE (0x5e) DW_TAG_subprogram)
+	.ascii "foo\0"	@ DW_AT_name
+	.byte	0x1	@ DW_AT_decl_file (tailcall.c)
+	.byte	0x1b	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB1	@ DW_AT_low_pc
+	.4byte	.LFE1-.LFB1	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.4byte	0x81	@ DW_AT_sibling
+	.uleb128 0x7	@ (DIE (0x77) DW_TAG_GNU_call_site)
+	.4byte	.LVL0	@ DW_AT_low_pc
+			@ DW_AT_GNU_tail_call
+	.4byte	0x81	@ DW_AT_abstract_origin
+	.byte	0	@ end of children of DIE 0x5e
+	.uleb128 0x8	@ (DIE (0x81) DW_TAG_subprogram)
+	.ascii "bar\0"	@ DW_AT_name
+	.byte	0x1	@ DW_AT_decl_file (tailcall.c)
+	.byte	0x15	@ DW_AT_decl_line
+			@ DW_AT_prototyped
+	.4byte	0x57	@ DW_AT_type
+	.4byte	.LFB0	@ DW_AT_low_pc
+	.4byte	.LFE0-.LFB0	@ DW_AT_high_pc
+	.uleb128 0x1	@ DW_AT_frame_base
+	.byte	0x9c	@ DW_OP_call_frame_cfa
+			@ DW_AT_GNU_all_call_sites
+	.byte	0	@ end of children of DIE 0xb
+	.section	.debug_abbrev,"",%progbits
+.Ldebug_abbrev0:
+	.uleb128 0x1	@ (abbrev code)
+	.uleb128 0x11	@ (TAG: DW_TAG_compile_unit)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x25	@ (DW_AT_producer)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x13	@ (DW_AT_language)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x1b	@ (DW_AT_comp_dir)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x55	@ (DW_AT_ranges)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x10	@ (DW_AT_stmt_list)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x2	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x3f	@ (DW_AT_external)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x1	@ (DW_AT_sibling)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x3	@ (abbrev code)
+	.uleb128 0x34	@ (TAG: DW_TAG_variable)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0xe	@ (DW_FORM_strp)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x2	@ (DW_AT_location)
+	.uleb128 0x17	@ (DW_FORM_sec_offset)
+	.byte	0
+	.byte	0
+	.uleb128 0x4	@ (abbrev code)
+	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)
+	.byte	0	@ DW_children_no
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x31	@ (DW_AT_abstract_origin)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x5	@ (abbrev code)
+	.uleb128 0x24	@ (TAG: DW_TAG_base_type)
+	.byte	0	@ DW_children_no
+	.uleb128 0xb	@ (DW_AT_byte_size)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3e	@ (DW_AT_encoding)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0x8	@ (DW_FORM_string)
+	.byte	0
+	.byte	0
+	.uleb128 0x6	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0x1	@ DW_children_yes
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0x8	@ (DW_FORM_string)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x1	@ (DW_AT_sibling)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x7	@ (abbrev code)
+	.uleb128 0x4109	@ (TAG: DW_TAG_GNU_call_site)
+	.byte	0	@ DW_children_no
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x2115	@ (DW_AT_GNU_tail_call)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x31	@ (DW_AT_abstract_origin)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.byte	0
+	.byte	0
+	.uleb128 0x8	@ (abbrev code)
+	.uleb128 0x2e	@ (TAG: DW_TAG_subprogram)
+	.byte	0	@ DW_children_no
+	.uleb128 0x3	@ (DW_AT_name)
+	.uleb128 0x8	@ (DW_FORM_string)
+	.uleb128 0x3a	@ (DW_AT_decl_file)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x3b	@ (DW_AT_decl_line)
+	.uleb128 0xb	@ (DW_FORM_data1)
+	.uleb128 0x27	@ (DW_AT_prototyped)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.uleb128 0x49	@ (DW_AT_type)
+	.uleb128 0x13	@ (DW_FORM_ref4)
+	.uleb128 0x11	@ (DW_AT_low_pc)
+	.uleb128 0x1	@ (DW_FORM_addr)
+	.uleb128 0x12	@ (DW_AT_high_pc)
+	.uleb128 0x6	@ (DW_FORM_data4)
+	.uleb128 0x40	@ (DW_AT_frame_base)
+	.uleb128 0x18	@ (DW_FORM_exprloc)
+	.uleb128 0x2117	@ (DW_AT_GNU_all_call_sites)
+	.uleb128 0x19	@ (DW_FORM_flag_present)
+	.byte	0
+	.byte	0
+	.byte	0
+	.section	.debug_loc,"",%progbits
+.Ldebug_loc0:
+.LLST0:
+	.4byte	.LVL1	@ Location list begin address (*.LLST0)
+	.4byte	.LVL2	@ Location list end address (*.LLST0)
+	.2byte	0x3	@ Location expression size
+	.byte	0x70	@ DW_OP_breg0
+	.sleb128 1
+	.byte	0x9f	@ DW_OP_stack_value
+	.4byte	.LVL2	@ Location list begin address (*.LLST0)
+	.4byte	.LFE2	@ Location list end address (*.LLST0)
+	.2byte	0x1	@ Location expression size
+	.byte	0x50	@ DW_OP_reg0
+	.4byte	0	@ Location list terminator begin (*.LLST0)
+	.4byte	0	@ Location list terminator end (*.LLST0)
+	.section	.debug_aranges,"",%progbits
+	.4byte	0x24	@ Length of Address Ranges Info
+	.2byte	0x2	@ DWARF Version
+	.4byte	.Ldebug_info0	@ Offset of Compilation Unit Info
+	.byte	0x4	@ Size of Address
+	.byte	0	@ Size of Segment Descriptor
+	.2byte	0	@ Pad to 8 byte boundary
+	.2byte	0
+	.4byte	.Ltext0	@ Address
+	.4byte	.Letext0-.Ltext0	@ Length
+	.4byte	.LFB2	@ Address
+	.4byte	.LFE2-.LFB2	@ Length
+	.4byte	0
+	.4byte	0
+	.section	.debug_ranges,"",%progbits
+.Ldebug_ranges0:
+	.4byte	.Ltext0	@ Offset 0
+	.4byte	.Letext0
+	.4byte	.LFB2	@ Offset 0x8
+	.4byte	.LFE2
+	.4byte	0
+	.4byte	0
+	.section	.debug_line,"",%progbits
+.Ldebug_line0:
+	.section	.debug_str,"MS",%progbits,1
+.LASF0:
+	.ascii	"GNU C11 7.4.0 -march=armv7-a -mfloat-abi=hard -mfpu"
+	.ascii	"=vfpv3-d16 -mthumb -mtls-dialect=gnu -g -O2 -fstack"
+	.ascii	"-protector-strong\000"
+.LASF4:
+	.ascii	"answer\000"
+.LASF1:
+	.ascii	"tailcall.c\000"
+.LASF2:
+	.ascii	"/home/ubuntu/development/gdb/binutils-gdb/gdb/tests"
+	.ascii	"uite/gdb.btrace\000"
+.LASF3:
+	.ascii	"main\000"
+	.ident	"GCC: (Ubuntu/Linaro 7.4.0-1ubuntu1~18.04.1) 7.4.0"
+	.section	.note.GNU-stack,"",%progbits
diff --git a/gdb/testsuite/gdb.btrace/buffer-size.exp b/gdb/testsuite/gdb.btrace/buffer-size.exp
index ea4e36c1593..23f859dce9c 100644
--- a/gdb/testsuite/gdb.btrace/buffer-size.exp
+++ b/gdb/testsuite/gdb.btrace/buffer-size.exp
@@ -32,10 +32,17 @@  if ![runto_main] {
     return -1
 }
 
-gdb_test_no_output "set record btrace bts buffer-size 1"
-gdb_test_no_output "set record btrace pt buffer-size 1"
-gdb_test "show record btrace bts buffer-size" "The record/replay bts buffer size is 1\.\r"
-gdb_test "show record btrace pt buffer-size" "The record/replay pt buffer size is 1\.\r"
+set btrace_type ""
+if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    set btrace_type { "bts" "pt" }
+} elseif {[istarget "arm*-*-*"]|| [istarget "aarch64*-*-*"]} {
+    set btrace_type { "etm" } 
+}
+
+foreach_with_prefix format $btrace_type {
+    gdb_test_no_output "set record btrace $format buffer-size 1"
+    gdb_test "show record btrace $format buffer-size" "The record/replay $format buffer size is 1\.\r"
+}
 
 gdb_test_no_output "record btrace"
 gdb_test "info record" [multi_line \
diff --git a/gdb/testsuite/gdb.btrace/instruction_history.exp b/gdb/testsuite/gdb.btrace/instruction_history.exp
index 403085c083f..3a6e7362f74 100644
--- a/gdb/testsuite/gdb.btrace/instruction_history.exp
+++ b/gdb/testsuite/gdb.btrace/instruction_history.exp
@@ -22,7 +22,17 @@  if { [skip_btrace_tests] } {
     return -1
 }
 
-standard_testfile .c .S
+set test_prefix ""
+if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    set test_prefix "x86"
+} elseif {[istarget "arm*-*-*"]} {
+    set test_prefix "arm"
+} elseif {[istarget "aarch64*-*-*"]} {
+    set test_prefix "aarch64"
+}
+
+standard_testfile instruction_history.c $test_prefix-instruction_history.S
+
 if [prepare_for_testing "failed to prepare" $testfile "$srcfile $srcfile2" {debug}] {
     return -1
 }
@@ -67,40 +77,108 @@  if { $traced != 11 } {
     pass $message
 }
 
-# test that we see the expected instructions
-gdb_test "record instruction-history 3,7" [multi_line \
+if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+  set test_pattern(0) "[multi_line \
       "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "4\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tdec    %eax" \
       "5\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "6\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \
       "7\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \
-  ]
-
-gdb_test "record instruction-history /f 3,+5" [multi_line \
+    ]"
+  set test_pattern(1) "[multi_line \
       "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tdec    %eax" \
       "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \
       "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \
-  ]
-
-gdb_test "record instruction-history /p 7,-5" [multi_line \
+      ]"
+  set test_pattern(2) "[multi_line \
       "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "4\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tdec    %eax" \
       "5\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "6\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \
       "7\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \
-  ]
-
-gdb_test "record instruction-history /pf 3,7" [multi_line \
+      ]"
+  set test_pattern(3) "[multi_line \
       "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tdec    %eax" \
       "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tjmp    0x\[0-9a-f\]+ <loop\\+\[0-9\]+>" \
       "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp    \\\$0x0,%eax" \
       "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r" \
-  ]
+      ]"
+  set test_pattern(4) "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r"
+} elseif {[istarget "arm*-*-*"]} {
+  set test_pattern(0) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \
+      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \
+      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \
+      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tr0, #0" \
+      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \
+      ]"
+  set test_pattern(1) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \
+      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \
+      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \
+      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tr0, #0" \
+      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \
+      ]"
+  set test_pattern(2) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \
+      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \
+      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \
+      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tr0, #0" \
+      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \
+      ]"
+  set test_pattern(3)  "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>" \
+      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tr0, r0, #1" \
+      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>" \
+      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tr0, #0" \
+      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r" \
+      ]"
+  set test_pattern(4) "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tbeq\t0x\[0-9a-f\]+ <L2>\r"
+} elseif {[istarget "aarch64*-*-*"]} {
+  set test_pattern(0) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*" \
+      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \
+      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \
+      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \
+      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \
+    ]"
+  set test_pattern(1) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*" \
+      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \
+      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \
+      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \
+      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \
+      ]"
+  set test_pattern(2) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*" \
+      "4\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \
+      "5\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \
+      "6\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \
+      "7\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \
+      ]"
+  set test_pattern(3) "[multi_line \
+      "3\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\\.eq\t0x\[0-9a-f\]+ <L2>.*" \
+      "4\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tsubs\tx0, x0, #0x1.*" \
+      "5\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\t0x\[0-9a-f\]+ <L1>.*" \
+      "6\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tcmp\tx0, #0x0.*" \
+      "7\t   0x\[0-9a-f\]+ <\\+\[0-9\]+>:\tb\\.eq\t0x\[0-9a-f\]+ <L2>.*\r" \
+      ]"
+  set test_pattern(4) "3\t   0x\[0-9a-f\]+ <L1\\+\[0-9\]+>:\tb\.eq\t0x\[0-9a-f\]+ <L2>  // b\.none\r"
+}
+
+# test that we see the expected instructions
+gdb_test "record instruction-history 3,7" $test_pattern(0)
+
+gdb_test "record instruction-history /f 3,+5" $test_pattern(1)
+
+gdb_test "record instruction-history /p 7,-5" $test_pattern(2)
+
+gdb_test "record instruction-history /pf 3,7"  $test_pattern(3)
 
-gdb_test "record instruction-history 3,3" "3\t   0x\[0-9a-f\]+ <loop\\+\[0-9\]+>:\tje     0x\[0-9a-f\]+ <loop\\+\[0-9\]+>\r"
+gdb_test "record instruction-history 3,3" $test_pattern(4)
 
 # the following tests are checking the iterators
 # to avoid lots of regexps, we just check the number of lines that
diff --git a/gdb/testsuite/gdb.btrace/non-stop.exp b/gdb/testsuite/gdb.btrace/non-stop.exp
index e509d65d660..fbc4cda7dd6 100644
--- a/gdb/testsuite/gdb.btrace/non-stop.exp
+++ b/gdb/testsuite/gdb.btrace/non-stop.exp
@@ -31,6 +31,12 @@  save_vars { GDBFLAGS } {
     clean_restart $testfile
 }
 
+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    set loop_position 2
+} elseif {[istarget "arm*-*-*"] || [istarget "aarch64*-*-*"]} {
+    set loop_position 3
+}
+
 if ![runto_main] {
     untested "failed to run to main"
     return -1
@@ -111,87 +117,99 @@  gdb_test "thread apply all info rec" ".*"
 gdb_test "info threads" ".*"
 
 with_test_prefix "navigate" {
-    gdb_test "thread apply 1 record goto 3" "$loop_line"
-    gdb_test "thread apply 2 record goto 4" "$loop_line"
+    gdb_test "thread apply 1 record goto [expr {$loop_position + 1}]" "$loop_line"
+    gdb_test "thread apply 2 record goto [expr {$loop_position + 2}]" "$loop_line"
     gdb_test "thread apply 1 info record" \
-        ".*Replay in progress\.  At instruction 3\." "thread 1 at insn 3"
+        ".*Replay in progress\.  At instruction [expr {$loop_position + 1}]\." "thread 1 at insn $loop_position"
     gdb_test "thread apply 2 info record" \
-        ".*Replay in progress\.  At instruction 4\." "thread 2 at insn 4"
+        ".*Replay in progress\.  At instruction [expr {$loop_position + 2}]\." "thread 2 at insn [expr {$loop_position + 2}]"
 
-    gdb_test "thread apply all record goto 5" "$loop_line"
+    gdb_test "thread apply all record goto [expr {$loop_position + 3}]" "$loop_line"
     gdb_test "thread apply 1 info record" \
-        ".*Replay in progress\.  At instruction 5\." "thread 1 at insn 5"
+        ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\." "thread 1 at insn [expr {$loop_position + 3}]"
     gdb_test "thread apply 2 info record" \
-        ".*Replay in progress\.  At instruction 5\." "thread 2 at insn 5"
+        ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\." "thread 2 at insn [expr {$loop_position + 3}]"
 }
 
 with_test_prefix "step" {
+    with_test_prefix "fixture" {
+	gdb_test "thread apply 1 record goto [expr {$loop_position + 3}]" ".*"
+	gdb_test "thread apply 2 record goto [expr {$loop_position + 3}]" ".*"
+    }
     with_test_prefix "thread 1" {
         gdb_test "thread apply 1 stepi 2" "$loop_line"
         gdb_test "thread apply 1 info record" \
-            ".*Replay in progress\.  At instruction 7\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 5}]\."
         gdb_test "thread apply 2 info record" \
-            ".*Replay in progress\.  At instruction 5\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."
     }
 
     with_test_prefix "thread 2" {
         gdb_test "thread apply 2 stepi 3" "$loop_line"
         gdb_test "thread apply 1 info record" \
-            ".*Replay in progress\.  At instruction 7\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 5}]\."
         gdb_test "thread apply 2 info record" \
-            ".*Replay in progress\.  At instruction 8\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 6}]\."
     }
 
     with_test_prefix "all" {
         gdb_cont_to all "stepi 4" "$loop_line" 2
         gdb_test "thread apply 1 info record" \
-            ".*Replay in progress\.  At instruction 11\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 9}]\."
         gdb_test "thread apply 2 info record" \
-            ".*Replay in progress\.  At instruction 12\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 10}]\."
     }
 }
 
 with_test_prefix "reverse-step" {
+    with_test_prefix "fixture" {
+        gdb_test "thread apply 1 record goto [expr {$loop_position + 9}]" ".*"
+        gdb_test "thread apply 2 record goto [expr {$loop_position + 10}]" ".*"
+    }
     with_test_prefix "thread 1" {
         gdb_test "thread apply 1 reverse-stepi 2" "$loop_line"
         gdb_test "thread apply 1 info record" \
-            ".*Replay in progress\.  At instruction 9\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 7}]\."
         gdb_test "thread apply 2 info record" \
-            ".*Replay in progress\.  At instruction 12\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 10}]\."
     }
 
     with_test_prefix "thread 2" {
         gdb_test "thread apply 2 reverse-stepi 3" "$loop_line"
         gdb_test "thread apply 1 info record" \
-            ".*Replay in progress\.  At instruction 9\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 7}]\."
         gdb_test "thread apply 2 info record" \
-            ".*Replay in progress\.  At instruction 9\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 7}]\."
     }
 
     with_test_prefix "all" {
         gdb_cont_to all "reverse-stepi 4" "$loop_line" 2
         gdb_test "thread apply 1 info record" \
-            ".*Replay in progress\.  At instruction 5\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."
         gdb_test "thread apply 2 info record" \
-            ".*Replay in progress\.  At instruction 5\."
+            ".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."
     }
 }
 
 with_test_prefix "continue" {
+    with_test_prefix "fixture" {
+	gdb_test "thread apply 1 record goto [expr {$loop_position + 3}]" ".*"
+	gdb_test "thread apply 2 record goto [expr {$loop_position + 3}]" ".*"
+    }
     with_test_prefix "thread 1" {
 	with_test_prefix "continue" {
 	    gdb_cont_to_no_history 1 "continue" 1
 	    gdb_test "thread apply 1 info record" \
 		".*Recorded \[0-9\]+ instructions \[^\\\r\\\n\]*"
 	    gdb_test "thread apply 2 info record" \
-		".*Replay in progress\.  At instruction 5\."
+		".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."
 	}
 	with_test_prefix "reverse-continue" {
 	    gdb_cont_to_no_history 1 "reverse-continue" 1
 	    gdb_test "thread apply 1 info record" \
 		".*Replay in progress\.  At instruction 1\."
 	    gdb_test "thread apply 2 info record" \
-		".*Replay in progress\.  At instruction 5\."
+		".*Replay in progress\.  At instruction [expr {$loop_position + 3}]\."
 	}
     }
 
diff --git a/gdb/testsuite/gdb.btrace/record_goto.exp b/gdb/testsuite/gdb.btrace/record_goto.exp
index 75d76da1c7f..267d4b412bc 100644
--- a/gdb/testsuite/gdb.btrace/record_goto.exp
+++ b/gdb/testsuite/gdb.btrace/record_goto.exp
@@ -35,21 +35,149 @@  if [info exists COMPILE] {
     # make check RUNTESTFLAGS="gdb.btrace/record_goto.exp COMPILE=1"
     standard_testfile record_goto.c
     lappend opts debug
-} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+} else {
+  set test_prefix ""
+  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
     if {[is_amd64_regs_target]} {
-		standard_testfile x86_64-record_goto.S
+      set test_prefix "x86_64"
     } else {
-		standard_testfile i686-record_goto.S
+      set test_prefix "i686"
     }
-} else {
+  } elseif {[istarget "arm*-*-*"]} {
+      set test_prefix "arm"
+  } elseif {[istarget "aarch64*-*-*"]} {
+    set test_prefix "aarch64"
+  } else {
     unsupported "target architecture not supported"
     return -1
+  }
+  standard_testfile $test_prefix-record_goto.S
 }
 
 if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {
     return -1
 }
 
+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    set function_positions(0) 19
+    set function_positions(1) 27
+    set function_positions(2) 2
+    set function_positions(end) 40
+    set function_positions(3) 39
+
+    set sequence_begin(1) 1
+    set sequence_end(1) 1
+    set sequence_begin(2) 2
+    set sequence_end(2) 4
+    set sequence_begin(3) 5
+    set sequence_end(3) 8
+    set sequence_begin(4) 9
+    set sequence_end(4) 9
+    set sequence_begin(5) 10
+    set sequence_end(5) 12
+    set sequence_begin(6) 13
+    set sequence_end(6) 16
+    set sequence_begin(7) 17
+    set sequence_end(7) 18
+    set sequence_begin(8) 19
+    set sequence_end(8) 19
+    set sequence_begin(9) 20
+    set sequence_end(9) 22
+    set sequence_begin(10) 23
+    set sequence_end(10) 26
+    set sequence_begin(11) 27
+    set sequence_end(11) 27
+    set sequence_begin(12) 28
+    set sequence_end(12) 30
+    set sequence_begin(13) 31
+    set sequence_end(13) 34
+    set sequence_begin(14) 35
+    set sequence_end(14) 36
+    set sequence_begin(15) 37
+    set sequence_end(15) 38
+    set sequence_begin(16) 39
+    set sequence_end(16) 40
+
+} elseif {[istarget "arm*-*-*"]} {
+    set function_positions(0) 23
+    set function_positions(1) 33
+    set function_positions(2) 2
+    set function_positions(end) 48
+    set function_positions(3) 47
+
+    set sequence_begin(1) 1
+    set sequence_end(1) 1
+    set sequence_begin(2) 2
+    set sequence_end(2) 4
+    set sequence_begin(3) 5
+    set sequence_end(3) 10
+    set sequence_begin(4) 11
+    set sequence_end(4) 11
+    set sequence_begin(5) 12
+    set sequence_end(5) 14
+    set sequence_begin(6) 15
+    set sequence_end(6) 20
+    set sequence_begin(7) 21
+    set sequence_end(7) 22
+    set sequence_begin(8) 23
+    set sequence_end(8) 23
+    set sequence_begin(9) 24
+    set sequence_end(9) 26
+    set sequence_begin(10) 27
+    set sequence_end(10) 32
+    set sequence_begin(11) 33
+    set sequence_end(11) 33
+    set sequence_begin(12) 34
+    set sequence_end(12) 36
+    set sequence_begin(13) 37
+    set sequence_end(13) 42
+    set sequence_begin(14) 43
+    set sequence_end(14) 44
+    set sequence_begin(15) 45
+    set sequence_end(15) 46
+    set sequence_begin(16) 47
+    set sequence_end(16) 48
+} elseif {[istarget "aarch64*-*-*"]} {
+    set function_positions(0) 16
+    set function_positions(1) 22
+    set function_positions(2) 2
+    set function_positions(end) 36
+    set function_positions(3) 35
+
+    set sequence_begin(1) 1
+    set sequence_end(1) 1
+    set sequence_begin(2) 2
+    set sequence_end(2) 4
+    set sequence_begin(3) 5
+    set sequence_end(3) 6
+    set sequence_begin(4) 7
+    set sequence_end(4) 7
+    set sequence_begin(5) 8
+    set sequence_end(5) 10
+    set sequence_begin(6) 11
+    set sequence_end(6) 12
+    set sequence_begin(7) 13
+    set sequence_end(7) 15
+    set sequence_begin(8) 16
+    set sequence_end(8) 16
+    set sequence_begin(9) 17
+    set sequence_end(9) 19
+    set sequence_begin(10) 20
+    set sequence_end(10) 21
+    set sequence_begin(11) 22
+    set sequence_end(11) 22
+    set sequence_begin(12) 23
+    set sequence_end(12) 25
+    set sequence_begin(13) 26
+    set sequence_end(13) 27
+    set sequence_begin(14) 28
+    set sequence_end(14) 30
+    set sequence_begin(15) 31
+    set sequence_end(15) 33
+    set sequence_begin(16) 34
+    set sequence_end(16) 36
+}
+
 if ![runto_main] {
     untested "failed to run to main"
     return -1
@@ -65,43 +193,43 @@  gdb_test "next"
 
 # start by listing all functions
 gdb_test "record function-call-history /ci 1, +20" [multi_line \
-  "1\tmain\tinst 1,1" \
-  "2\t  fun4\tinst 2,4" \
-  "3\t    fun1\tinst 5,8" \
-  "4\t  fun4\tinst 9,9" \
-  "5\t    fun2\tinst 10,12" \
-  "6\t      fun1\tinst 13,16" \
-  "7\t    fun2\tinst 17,18" \
-  "8\t  fun4\tinst 19,19" \
-  "9\t    fun3\tinst 20,22" \
-  "10\t      fun1\tinst 23,26" \
-  "11\t    fun3\tinst 27,27" \
-  "12\t      fun2\tinst 28,30" \
-  "13\t        fun1\tinst 31,34" \
-  "14\t      fun2\tinst 35,36" \
-  "15\t    fun3\tinst 37,38" \
-  "16\t  fun4\tinst 39,40" \
+  "1\tmain\tinst $sequence_begin(1),$sequence_end(1)" \
+  "2\t  fun4\tinst $sequence_begin(2),$sequence_end(2)" \
+  "3\t    fun1\tinst $sequence_begin(3),$sequence_end(3)" \
+  "4\t  fun4\tinst $sequence_begin(4),$sequence_end(4)" \
+  "5\t    fun2\tinst $sequence_begin(5),$sequence_end(5)" \
+  "6\t      fun1\tinst $sequence_begin(6),$sequence_end(6)" \
+  "7\t    fun2\tinst $sequence_begin(7),$sequence_end(7)" \
+  "8\t  fun4\tinst $sequence_begin(8),$sequence_end(8)" \
+  "9\t    fun3\tinst $sequence_begin(9),$sequence_end(9)" \
+  "10\t      fun1\tinst $sequence_begin(10),$sequence_end(10)" \
+  "11\t    fun3\tinst $sequence_begin(11),$sequence_end(11)" \
+  "12\t      fun2\tinst $sequence_begin(12),$sequence_end(12)" \
+  "13\t        fun1\tinst $sequence_begin(13),$sequence_end(13)" \
+  "14\t      fun2\tinst $sequence_begin(14),$sequence_end(14)" \
+  "15\t    fun3\tinst $sequence_begin(15),$sequence_end(15)" \
+  "16\t  fun4\tinst $sequence_begin(16),$sequence_end(16)" \
   ]
 
 # let's see if we can go back in history
-gdb_test "record goto 19" ".*fun4 \\(\\) at record_goto.c:43.*"
+gdb_test "record goto $function_positions(0)" ".*fun4 \\(\\) at record_goto.c:43.*"
 
 # the function call history should start at the new location
 gdb_test "record function-call-history /ci" [multi_line \
-  "8\t  fun4\tinst 19,19" \
-  "9\t    fun3\tinst 20,22" \
-  "10\t      fun1\tinst 23,26" \
-  ] "function-call-history from 19 forwards"
+  "8\t  fun4\tinst $sequence_begin(8),$sequence_end(8)" \
+  "9\t    fun3\tinst $sequence_begin(9),$sequence_end(9)" \
+  "10\t      fun1\tinst $sequence_begin(10),$sequence_end(10)" \
+  ] "function-call-history from $function_positions(0) forwards"
 
 # the instruction history should start at the new location
 gdb_test "record instruction-history" [multi_line \
-  "19.*" \
-  "20.*" \
-  "21.*" \
-  ] "instruction-history from 19 forwards"
+  "$function_positions(0).*" \
+  "[expr {$function_positions(0) + 1}].*" \
+  "[expr {$function_positions(0) + 2}].*" \
+  ] "instruction-history from $function_positions(0) forwards"
 
 # let's go to another place in the history
-gdb_test "record goto 27" ".*fun3 \\(\\) at record_goto.c:35.*"
+gdb_test "record goto $function_positions(1)" ".*fun3 \\(\\) at record_goto.c:35.*"
 
 # check the back trace at that location
 gdb_test "backtrace" [multi_line \
@@ -117,26 +245,26 @@  gdb_test "up" ".*main.*at record_goto.c:49.*" "up to main"
 
 # the function call history should start at the new location
 gdb_test "record function-call-history /ci -" [multi_line \
-  "9\t    fun3\tinst 20,22" \
-  "10\t      fun1\tinst 23,26" \
-  "11\t    fun3\tinst 27,27" \
-  ] "function-call-history from 27 backwards"
+  "9\t    fun3\tinst $sequence_begin(9),$sequence_end(9)" \
+  "10\t      fun1\tinst $sequence_begin(10),$sequence_end(10)" \
+  "11\t    fun3\tinst $sequence_begin(11),$sequence_end(11)" \
+  ] "function-call-history from $function_positions(1) backwards"
 
 # the instruction history should start at the new location
 gdb_test "record instruction-history -" [multi_line \
-  "25.*" \
-  "26.*" \
-  "27.*" \
-  ] "instruction-history from 27 backwards"
+  "[expr {$function_positions(1) - 2}].*" \
+  "[expr {$function_positions(1) - 1}].*" \
+  "$function_positions(1).*" \
+  ] "instruction-history from $function_positions(1) backwards"
 
 # test that we can go to the begin of the trace
 gdb_test "record goto begin" ".*main \\(\\) at record_goto.c:49.*"
 
 # check that we're filling up the context correctly
 gdb_test "record function-call-history /ci -" [multi_line \
-  "1\tmain\tinst 1,1" \
-  "2\t  fun4\tinst 2,4" \
-  "3\t    fun1\tinst 5,8" \
+  "1\tmain\tinst $sequence_begin(1),$sequence_end(1)" \
+  "2\t  fun4\tinst $sequence_begin(2),$sequence_end(2)" \
+  "3\t    fun1\tinst $sequence_begin(3),$sequence_end(3)" \
   ] "function-call-history from begin backwards"
 
 # check that we're filling up the context correctly
@@ -147,52 +275,53 @@  gdb_test "record instruction-history -" [multi_line \
   ] "instruction-history from begin backwards"
 
 # we should get the exact same history from the first instruction
-gdb_test "record goto 2" ".*fun4 \\(\\) at record_goto.c:40.*"
+gdb_test "record goto $function_positions(2)" ".*fun4 \\(\\) at record_goto.c:40.*"
 
 # check that we're filling up the context correctly
 gdb_test "record function-call-history /ci -" [multi_line \
-  "1\tmain\tinst 1,1" \
-  "2\t  fun4\tinst 2,4" \
-  "3\t    fun1\tinst 5,8\r" \
-  ] "function-call-history from 2 backwards"
+  "1\tmain\tinst $sequence_begin(1),$sequence_end(1)" \
+  "2\t  fun4\tinst $sequence_begin(2),$sequence_end(2)" \
+  "3\t    fun1\tinst $sequence_begin(3),$sequence_end(3)\r" \
+  ] "function-call-history from $function_positions(2) backwards"
 
 # check that we're filling up the context correctly
 gdb_test "record instruction-history -" [multi_line \
   "1.*" \
   "2.*" \
   "3.*" \
-  ] "instruction-history from 2 backwards"
+  ] "instruction-history from $function_positions(2) backwards"
 
 # check that we can go to the end of the trace
 gdb_test "record goto end" ".*main \\(\\) at record_goto.c:50.*"
 
 # check that we're filling up the context correctly
 gdb_test "record function-call-history /ci" [multi_line \
-  "14\t      fun2\tinst 35,36" \
-  "15\t    fun3\tinst 37,38" \
-  "16\t  fun4\tinst 39,40" \
+  "14\t      fun2\tinst $sequence_begin(14),$sequence_end(14)" \
+  "15\t    fun3\tinst $sequence_begin(15),$sequence_end(15)" \
+  "16\t  fun4\tinst $sequence_begin(16),$sequence_end(16)" \
   ] "function-call-history from end forwards"
 
 # check that we're filling up the context correctly
+#adapt it for arm, last instruction is  at pos 48
 gdb_test "record instruction-history" [multi_line \
-  "38.*" \
-  "39.*" \
-  "40.*\r" \
+  "[expr {$function_positions(end) - 2}].*" \
+  "[expr {$function_positions(end) - 1}].*" \
+  "$function_positions(end).*\r" \
   ] "instruction-history from end forwards"
 
 # we should get the exact same history from the second to last instruction
-gdb_test "record goto 39" ".*fun4 \\(\\) at record_goto.c:44.*"
+gdb_test "record goto $function_positions(3)" ".*fun4 \\(\\) at record_goto.c:44.*"
 
 # check that we're filling up the context correctly
 gdb_test "record function-call-history /ci" [multi_line \
-  "14\t      fun2\tinst 35,36" \
-  "15\t    fun3\tinst 37,38" \
-  "16\t  fun4\tinst 39,40\r" \
-  ] "function-call-history from 39 forwards"
+  "14\t      fun2\tinst $sequence_begin(14),$sequence_end(14)" \
+  "15\t    fun3\tinst $sequence_begin(15),$sequence_end(15)" \
+  "16\t  fun4\tinst $sequence_begin(16),$sequence_end(16)\r" \
+  ] "function-call-history from $function_positions(3) forwards"
 
 # check that we're filling up the context correctly
 gdb_test "record instruction-history" [multi_line \
-  "38.*" \
-  "39.*" \
-  "40.*\r" \
-  ] "instruction-history from 39 forwards"
+  "[expr {$function_positions(3) - 1}].*" \
+  "$function_positions(3).*" \
+  "[expr {$function_positions(3) + 1}].*\r" \
+  ] "instruction-history from $function_positions(3) forwards"
diff --git a/gdb/testsuite/gdb.btrace/stepi.exp b/gdb/testsuite/gdb.btrace/stepi.exp
index 480c08c4875..f07961228e0 100644
--- a/gdb/testsuite/gdb.btrace/stepi.exp
+++ b/gdb/testsuite/gdb.btrace/stepi.exp
@@ -33,21 +33,79 @@  if [info exists COMPILE] {
     # make check RUNTESTFLAGS="gdb.btrace/stepi.exp COMPILE=1"
     standard_testfile record_goto.c
     lappend opts debug
-} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+} else {
+  set test_prefix ""
+  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
     if {[is_amd64_regs_target]} {
-		standard_testfile x86_64-record_goto.S
+      set test_prefix "x86_64"
     } else {
-		standard_testfile i686-record_goto.S
+      set test_prefix "i686"
     }
-} else {
+  } elseif {[istarget "arm*-*-*"]} {
+      set test_prefix "arm"
+  } elseif {[istarget "aarch64*-*-*"]} {
+    set test_prefix "aarch64"
+  } else {
     unsupported "target architecture not supported"
     return -1
+  }
+  standard_testfile $test_prefix-record_goto.S
 }
 
 if [prepare_for_testing "failed to prepare" $testfile $srcfile {}] {
     return -1
 }
 
+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    set instructions_count 40
+    set instruction_position(0) 39
+    set instruction_position(1) 40
+    set instruction_position(2) 1
+    set instruction_position(3) 1
+    set instruction_position(4) 22
+    set instruction_position(5) 23
+    set instruction_position(6) 22
+    set instruction_position(7) 27
+    set instruction_position(8) 22
+    set instruction_position(9) 1
+    set instruction_position(10) 1
+    set instruction_position(11) 1
+    set instruction_position(12) 2
+    set instruction_position(13) 1
+} elseif {[istarget "arm*-*-*"]} {
+    set instructions_count 48
+    set instruction_position(0) 47
+    set instruction_position(1) 48
+    set instruction_position(2) 1
+    set instruction_position(3) 1
+    set instruction_position(4) 26
+    set instruction_position(5) 27
+    set instruction_position(6) 26
+    set instruction_position(7) 33
+    set instruction_position(8) 26
+    set instruction_position(9) 1
+    set instruction_position(10) 1
+    set instruction_position(11) 1
+    set instruction_position(12) 2
+    set instruction_position(13) 1
+} elseif {[istarget "aarch64*-*-*"]} {
+    set instructions_count 36
+    set instruction_position(0) 35
+    set instruction_position(1) 36
+    set instruction_position(2) 1
+    set instruction_position(3) 1
+    set instruction_position(4) 19
+    set instruction_position(5) 20
+    set instruction_position(6) 19
+    set instruction_position(7) 22
+    set instruction_position(8) 19
+    set instruction_position(9) 1
+    set instruction_position(10) 1
+    set instruction_position(11) 1
+    set instruction_position(12) 2
+    set instruction_position(13) 1
+}
+
 if ![runto_main] {
     untested "failed to run to main"
     return -1
@@ -56,10 +114,11 @@  if ![runto_main] {
 global gdb_prompt
 
 proc check_replay_at { insn } {
+  global instructions_count
   gdb_test "info record" [multi_line \
     "Active record target: record-btrace" \
     ".*" \
-    "Recorded 40 instructions in 16 functions \\\(0 gaps\\\) for .*" \
+    "Recorded $instructions_count instructions in 16 functions \\\(0 gaps\\\) for .*" \
     "Replay in progress\.  At instruction $insn\." \
     ] "check replay at $insn"
 }
@@ -74,15 +133,14 @@  with_test_prefix "record" {
 with_test_prefix "fetch" {
     gdb_test "reverse-stepi" ".*fun4\.5.*" "reverse-stepi.1"
     gdb_test "reverse-stepi" ".*fun4\.5.*" "reverse-stepi.2"
-
     # let's check where we are in the trace
-    check_replay_at 39
+    check_replay_at $instruction_position(0) 
 }
 
 # let's step forward and check again
 with_test_prefix "stepi" {
     gdb_test "stepi" ".*fun4\.5.*"
-    check_replay_at 40
+    check_replay_at $instruction_position(1) 
 }
 
 # with the next step, we stop replaying
@@ -91,14 +149,17 @@  with_test_prefix "end" {
     gdb_test "info record" [multi_line \
       "Active record target: record-btrace" \
       ".*" \
-      "Recorded 40 instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \
+      "Recorded $instructions_count instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \
   ] 
 }
 
+#recover from a missing lr register in arm
+gdb_test "record goto end"
+
 # let's try nexti
 with_test_prefix "reverse-nexti.1" {
     gdb_test "reverse-nexti" ".*main\.2.*"
-    check_replay_at 1
+    check_replay_at $instruction_position(2)
 }
 
 # we can't reverse-nexti any further
@@ -106,7 +167,7 @@  with_test_prefix "reverse-nexti.2" {
     gdb_test "reverse-nexti" \
 	"No more reverse-execution history\.\r\n.*main\.2.*" \
 	"reverse-nexti.2"
-    check_replay_at 1
+    check_replay_at $instruction_position(3)
 }
 
 # but we can step back again
@@ -115,32 +176,32 @@  with_test_prefix "nexti" {
     gdb_test "info record" [multi_line \
       "Active record target: record-btrace" \
       ".*" \
-      "Recorded 40 instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \
+      "Recorded $instructions_count instructions in 16 functions \\\(0 gaps\\\) for \[^\\\r\\\n\]*" \
 			       ]
 }
 
 # let's step from a goto position somewhere in the middle
 with_test_prefix "goto" {
-    gdb_test "record goto 22" ".*fun3\.2.*"
-    with_test_prefix "goto 22" { check_replay_at 22 }
+    gdb_test "record goto $instruction_position(4) " ".*fun3\.2.*"
+    with_test_prefix "goto $instruction_position(4) " { check_replay_at $instruction_position(4)  }
 
     gdb_test "stepi" ".*fun1\.1.*" "stepi.3"
-    with_test_prefix "stepi to 23" { check_replay_at 23 }
+    with_test_prefix "stepi to $instruction_position(5)" { check_replay_at $instruction_position(5) }
 
     gdb_test "reverse-stepi" ".*fun3\.2.*" "reverse-stepi.3"
-    with_test_prefix "reverse-stepi to 22" { check_replay_at 22 }
+    with_test_prefix "reverse-stepi to $instruction_position(6)" { check_replay_at $instruction_position(6) }
 
     gdb_test "nexti" ".*fun3\.3.*"
-    with_test_prefix "nexti to 27" { check_replay_at 27 }
+    with_test_prefix "nexti to $instruction_position(7) " { check_replay_at $instruction_position(7)  }
 
     gdb_test "reverse-nexti" ".*fun3\.2.*" "reverse-nexti.3"
-    with_test_prefix "reverse-nexti to 22" { check_replay_at 22 }
+    with_test_prefix "reverse-nexti to $instruction_position(8)" { check_replay_at $instruction_position(8) }
 }
 
 # let's try to step off the left end
 with_test_prefix "goto begin" {
     gdb_test "record goto begin" ".*main\.2.*"
-    check_replay_at 1
+    check_replay_at $instruction_position(9)
 
     with_test_prefix "reverse-stepi" {
 	gdb_test "reverse-stepi" \
@@ -149,7 +210,7 @@  with_test_prefix "goto begin" {
 	gdb_test "reverse-stepi" \
 	    "No more reverse-execution history\.\r\n.*main\.2.*" \
 	    "reverse-stepi.2"
-	check_replay_at 1
+	check_replay_at $instruction_position(10)
     }
 
     with_test_prefix "reverse-nexti" {
@@ -159,13 +220,13 @@  with_test_prefix "goto begin" {
 	gdb_test "reverse-nexti" \
 	    "No more reverse-execution history\.\r\n.*main\.2.*" \
 	    "reverse-nexti.2"
-	check_replay_at 1
+	check_replay_at $instruction_position(11)
     }
 
     # we can step forward, though
     with_test_prefix "stepi" {
 	gdb_test "stepi" ".*fun4\.1.*"
-	check_replay_at 2
+	check_replay_at $instruction_position(12)
     }
 }
 
@@ -178,5 +239,5 @@  with_test_prefix "reverse-stepi" {
     gdb_test "reverse-stepi" \
 	"No more reverse-execution history\.\r\n.*main\.2.*" \
 	"reverse-stepi.3"
-    check_replay_at 1
+    check_replay_at $instruction_position(13)
 }
diff --git a/gdb/testsuite/gdb.btrace/tailcall-only.exp b/gdb/testsuite/gdb.btrace/tailcall-only.exp
index 510f90c9d5e..036da4a2020 100644
--- a/gdb/testsuite/gdb.btrace/tailcall-only.exp
+++ b/gdb/testsuite/gdb.btrace/tailcall-only.exp
@@ -37,15 +37,23 @@  if [info exists COMPILE] {
     # make check RUNTESTFLAGS="gdb.btrace/tailcall-only.exp COMPILE=1"
     standard_testfile tailcall-only.c
     lappend opts debug optimize=-O2
-} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+} else {
+  set test_prefix ""
+  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
     if {[is_amd64_regs_target]} {
-		standard_testfile x86_64-tailcall-only.S
+      set test_prefix "x86_64"
     } else {
-		standard_testfile i686-tailcall-only.S
+      set test_prefix "i686"
     }
-} else {
+  } elseif {[istarget "arm*-*-*"]} {
+      set test_prefix "arm"
+  } elseif {[istarget "aarch64*-*-*"]} {
+    set test_prefix "aarch64"
+  } else {
     unsupported "target architecture not supported"
     return -1
+  }
+  standard_testfile $test_prefix-tailcall-only.S
 }
 
 if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {
@@ -62,6 +70,10 @@  gdb_test_no_output "set record function-call-history-size 0"
 
 # trace foo
 gdb_test "step" ".*" "prepare for recording"
+# make sure we get out of function epilogue
+if { [istarget "arm*-*-*"] } {
+  gdb_test "stepi"
+}
 gdb_test_no_output "record btrace"
 gdb_test "stepi 4" ".*" "record branch trace"
 
diff --git a/gdb/testsuite/gdb.btrace/tailcall.exp b/gdb/testsuite/gdb.btrace/tailcall.exp
index 07a3ec103f4..70fda8a5670 100644
--- a/gdb/testsuite/gdb.btrace/tailcall.exp
+++ b/gdb/testsuite/gdb.btrace/tailcall.exp
@@ -34,20 +34,42 @@  if [info exists COMPILE] {
     # make check RUNTESTFLAGS="gdb.btrace/tailcall.exp COMPILE=1"
     standard_testfile tailcall.c
     lappend opts debug optimize=-O2
-} elseif {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+} else {
+  set test_prefix ""
+  if { [istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
     if {[is_amd64_regs_target]} {
-		standard_testfile x86_64-tailcall.S
+      set test_prefix "x86_64"
     } else {
-		standard_testfile i686-tailcall.S
+      set test_prefix "i686"
     }
-} else {
+  } elseif {[istarget "arm*-*-*"]} {
+      set test_prefix "arm"
+  } elseif {[istarget "aarch64*-*-*"]} {
+    set test_prefix "aarch64"
+  } else {
     unsupported "target architecture not supported"
     return -1
+  }
+  standard_testfile $test_prefix-tailcall.S
 }
 
 if [prepare_for_testing "failed to prepare" $testfile $srcfile $opts] {
     return -1
 }
+
+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    set bar_return_line 24
+    set bar_return_position 4
+    set main_return_line 38
+} elseif {[istarget "arm*-*-*"]} {
+    set bar_return_line 24
+    set bar_return_position 5
+    set main_return_line 41
+    } elseif {[istarget "aarch64*-*-*"]} {
+    set bar_return_line 23
+    set bar_return_position 6
+    set main_return_line 40
+}
 if ![runto_main] {
     untested "failed to run to main"
     return -1
@@ -58,7 +80,17 @@  gdb_test_no_output "set record function-call-history-size 0"
 
 # trace the call to foo
 gdb_test_no_output "record btrace"
-gdb_test "next 2"
+
+# make sure we get out of function epilogue
+if {[istarget "i?86-*-*"] || [istarget "x86_64-*-*"]} {
+    gdb_test "next 2"
+} elseif {[istarget "arm*-*-*"]} {
+  gdb_test "next 2"
+  gdb_test "stepi"
+} elseif {[istarget "aarch64*-*-*"]} {
+  gdb_test "next"
+  gdb_test "stepi 2"
+}
 
 # show the flat branch trace
 gdb_test "record function-call-history 1" [multi_line \
@@ -77,11 +109,11 @@  gdb_test "record function-call-history /c 1" [multi_line \
   ] "indented"
 
 # go into bar
-gdb_test "record goto 4" ".*bar \\(\\) at .*tailcall.c:24\r\n.*"
+gdb_test "record goto $bar_return_position" ".*bar \\(\\) at .*tailcall.c:$bar_return_line\r\n.*"
 
 # check the backtrace
 gdb_test "backtrace" [multi_line \
-  "#0.*bar \\(\\) at tailcall.c:24" \
+  "#0.*bar \\(\\) at tailcall.c:$bar_return_line" \
   "#1.*foo \\(\\) at tailcall.c:29" \
   "#2.*main \\(\\) at tailcall.c:37" \
   "Backtrace stopped: not enough registers or memory available to unwind further" \
@@ -93,23 +125,23 @@  gdb_test "up" "#2\[^\r\n\]*main \\(\\) at tailcall.c:37\r\n.*" "up to main"
 gdb_test "down" "#1\[^\r\n\]*foo \\(\\) at tailcall.c:29\r\n.*" "down to foo"
 
 # test stepping into and out of tailcalls.
-gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:38\r\n.*" \
+gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:$main_return_line\r\n.*" \
     "finish.1"
-gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:24\r\n.*" \
+gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:$bar_return_line\r\n.*" \
     "reverse-step.1"
 gdb_test "reverse-finish" "\[^\r\n\]*foo \\(\\) at tailcall.c:29\r\n.*" \
     "reverse-finish.1"
 gdb_test "reverse-step" "\[^\r\n\]*main \\(\\) at tailcall.c:37\r\n.*" \
     "reverse-step.2"
-gdb_test "next" "\[^\r\n\]*38.*" \
+gdb_test "next" "\[^\r\n\]*$main_return_line.*" \
     "next.1"
 gdb_test "reverse-next" "\[^\r\n\]*main \\(\\) at tailcall.c:37\r\n.*" \
     "reverse-next.1"
 gdb_test "step" "\[^\r\n\]*foo \\(\\) at tailcall.c:29\r\n.*" \
     "step.1"
-gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:38\r\n.*" \
+gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:$main_return_line\r\n.*" \
     "finish.2"
-gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:24\r\n.*" \
+gdb_test "reverse-step" "\[^\r\n\]*bar \\(\\) at tailcall.c:$bar_return_line\r\n.*" \
     "reverse-step.3"
-gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:38\r\n.*" \
+gdb_test "finish" "\[^\r\n\]*main \\(\\) at tailcall.c:$main_return_line\r\n.*" \
     "finish.3"
diff --git a/gdb/testsuite/gdb.btrace/instruction_history.S b/gdb/testsuite/gdb.btrace/x86-instruction_history.S
similarity index 100%
rename from gdb/testsuite/gdb.btrace/instruction_history.S
rename to gdb/testsuite/gdb.btrace/x86-instruction_history.S
diff --git a/gdb/testsuite/lib/gdb.exp b/gdb/testsuite/lib/gdb.exp
index 36a5fd4feb7..02cf8a3cec6 100644
--- a/gdb/testsuite/lib/gdb.exp
+++ b/gdb/testsuite/lib/gdb.exp
@@ -3248,7 +3248,7 @@  gdb_caching_proc skip_btrace_tests {
     global srcdir subdir gdb_prompt inferior_exited_re
 
     set me "skip_btrace_tests"
-    if { ![istarget "i?86-*-*"] && ![istarget "x86_64-*-*"] } {
+    if { ![istarget "i?86-*-*"] && ![istarget "x86_64-*-*"] && ![istarget "arm*-*-*"] && ![istarget "aarch64*-*-*"]} {
         verbose "$me:  target does not support btrace, returning 1" 2
         return 1
     }